免费注册 查看新帖 |

Chinaunix

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

[Linux] [结贴]给shmat返回的指针,指向的内容赋值,崩溃了,为什么? [复制链接]

论坛徽章:
2
2015年迎新春徽章
日期:2015-03-04 10:16:532015元宵节徽章
日期:2015-03-06 15:53:22
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2015-03-02 11:13 |只看该作者 |倒序浏览
本帖最后由 cdsfiui 于 2015-03-03 14:08 编辑

我写了另一个很小的程序,试图来学习一下shmat的用法,不想其返回的指针一调用就崩溃。

  1. #include<stdio.h>
  2. #include<stdlib.h>
  3. #include<unistd.h>
  4. #include<fcntl.h>
  5. #include<sys/ipc.h>
  6. #include<sys/shm.h>
  7. #include<sys/types.h>
  8. #include<sys/wait.h>
  9. #include<assert.h>
  10. int main()
  11. {
  12.   key_t k=ftok("s",'1');
  13.   pid_t id=fork();
  14.   if(id==0)//
  15.   {
  16.     printf("child begin\n");
  17.     int fd=shmget(k,1000,IPC_CREAT);
  18.     assert(fd!=-1);
  19.     void* p=shmat(fd,NULL,0);
  20.     printf("shmat OK\n");
  21.     int* pi=(int*)p;
  22.     *pi=2;
  23.     printf("child ends\n");
  24.     shmdt(p);
  25.   }
  26.   else if(id>0)//father
  27.   {
  28.     printf("father begin\n");
  29.     int status;
  30.     wait(&status);
  31.     int fd=shmget(k,1000,IPC_PRIVATE);
  32.     assert(fd!=-1);
  33.     void* p=shmat(fd,NULL,0);
  34.     printf("shmat OK\n");
  35.     int *pi=(int*)p;
  36.     printf("pi=%d\n",*pi);
  37.     printf("father ends\n");
  38.     shmdt(p);
  39.   }
  40.   return 0;
  41. }
复制代码
编译运行这个程序,输出的是:

  1. father begin
  2. child begin
  3. shmat OK
  4. shmat OK
  5. Segmentation fault (core dumped)
复制代码
请问: 我的程序错在哪里呢?

求职 : 机器学习
论坛徽章:
79
2015年亚洲杯纪念徽章
日期:2015-05-06 19:18:572015七夕节徽章
日期:2015-08-21 11:06:172015亚冠之阿尔纳斯尔
日期:2015-09-07 09:30:232015亚冠之萨济拖拉机
日期:2015-10-21 08:26:3915-16赛季CBA联赛之浙江
日期:2015-12-30 09:59:1815-16赛季CBA联赛之浙江
日期:2016-01-10 12:35:21技术图书徽章
日期:2016-01-15 11:07:2015-16赛季CBA联赛之新疆
日期:2016-02-24 13:46:0215-16赛季CBA联赛之吉林
日期:2016-06-26 01:07:172015-2016NBA季后赛纪念章
日期:2016-06-28 17:44:45黑曼巴
日期:2016-06-28 17:44:4515-16赛季CBA联赛之浙江
日期:2017-07-18 13:41:54
2 [报告]
发表于 2015-03-02 12:37 |只看该作者
本帖最后由 zsszss0000 于 2015-03-02 12:37 编辑
  1. Program received signal SIGSEGV, Segmentation fault.
复制代码
你的程序收到了SIGSEGV信号。
  1. void* p=shmat(fd,NULL,0);
复制代码
这行代码得到的p的结果是 (void *) 0xffffffffffffffff.
所以,应该是非法地址的访问造成的程序出错。
建议查查void* p=shmat(fd,NULL,0);这一句是否有问题。

论坛徽章:
2
2015年迎新春徽章
日期:2015-03-04 10:16:532015元宵节徽章
日期:2015-03-06 15:53:22
3 [报告]
发表于 2015-03-02 13:15 |只看该作者
zsszss0000 发表于 2015-03-02 12:37
你的程序收到了SIGSEGV信号。这行代码得到的p的结果是 (void *) 0xffffffffffffffff.
所以,应该是非法地址 ...


这一句返回一个非法的指针,ok,可是为什么会调用失败返回非法的指针呢? ftok函数的参数"s"是一个已经存在的文件,就在当前目录。

我又尝试了一下网上找到的例子:
blog.csdn.net/lanmanck/article/details/6092884

在运行程序之前先touch /dev/shm/myshm2
结果还是一样,程序运行崩溃了。

实在是不明白了。我的程序错在哪里?

论坛徽章:
4
双子座
日期:2014-08-28 10:08:002015年辞旧岁徽章
日期:2015-03-03 16:54:152015年迎新春徽章
日期:2015-03-04 09:58:112015年亚洲杯之阿联酋
日期:2015-03-13 03:25:15
4 [报告]
发表于 2015-03-02 14:17 |只看该作者
gdb看一下呗,另外ipcs看看系统是否创建了共享内存

论坛徽章:
2
2015年迎新春徽章
日期:2015-03-04 10:16:532015元宵节徽章
日期:2015-03-06 15:53:22
5 [报告]
发表于 2015-03-02 16:35 |只看该作者
weishuo1999 发表于 2015-03-02 14:17
gdb看一下呗,另外ipcs看看系统是否创建了共享内存


创建了。
另外: 我测试了一下,发现root用户就可以运行这个程序,打印我期待的输出,没有问题。

可是如果是权限的问题,难道说,普通用户还不能使用共享内存,非得是root用户? 说不通啊

论坛徽章:
4
双子座
日期:2014-08-28 10:08:002015年辞旧岁徽章
日期:2015-03-03 16:54:152015年迎新春徽章
日期:2015-03-04 09:58:112015年亚洲杯之阿联酋
日期:2015-03-13 03:25:15
6 [报告]
发表于 2015-03-02 17:55 |只看该作者
你看看你create的时候的权限是什么,还有是不是root创建的,另外可以打一下错误信息,strerror函数看看就知道了,要是root创建的共享内存,凭啥你能写呢?

论坛徽章:
2
2015年迎新春徽章
日期:2015-03-04 10:16:532015元宵节徽章
日期:2015-03-06 15:53:22
7 [报告]
发表于 2015-03-02 18:08 |只看该作者
weishuo1999 发表于 2015-03-02 17:55
你看看你create的时候的权限是什么,还有是不是root创建的,另外可以打一下错误信息,strerror函数看看就知 ...


ftok的参数是"s",这个是我用普通用户创建的一个空文件。
我按照你说的,加了对errno的打印,发现错误代码是13,代码如下:

  1. #include<errno.h>
  2. #include<stdio.h>
  3. #include<stdlib.h>
  4. #include<unistd.h>
  5. #include<fcntl.h>
  6. #include<sys/ipc.h>
  7. #include<sys/shm.h>
  8. #include<sys/types.h>
  9. #include<sys/wait.h>
  10. #include<assert.h>
  11. int main()
  12. {
  13.   key_t k=ftok("s",'1');
  14.   pid_t id=fork();
  15.   if(id==0)//
  16.   {
  17.     printf("child begin\n");
  18.     int fd=shmget(k,1000,IPC_CREAT);
  19.     assert(fd!=-1);
  20.     void* p=shmat(fd,NULL,0);
  21.     printf("shmat OK\n");

  22.     long res = (long)p;
  23.     if(res<0)
  24.     {
  25.         printf(" res < 0  error = %d\n", errno);
  26.         return 0;
  27.     }
  28.     int* pi=(int*)p;
  29.     *pi=2;
  30.     printf("child ends\n");
  31.     shmdt(p);
  32.   }
  33.   else if(id>0)//father
  34.   {
  35.     printf("father begin\n");
  36.     int status;
  37.     wait(&status);
  38.     int fd=shmget(k,1000,IPC_CREAT);
  39.     assert(fd!=-1);
  40.     void* p=shmat(fd,NULL,0);
  41.     printf("shmat OK\n");

  42.     long res = (long)p;
  43.     if(res<0)
  44.     {
  45.         printf(" res < 0  error = %d\n", errno);
  46.         return 0;
  47.     }
  48.     int *pi=(int*)p;
  49.     printf("pi=%d\n",*pi);
  50.     printf("father ends\n");
  51.     shmdt(p);
  52.   }
  53.   return 0;
  54. }
复制代码
普通用户的运行输出如下:

  1. father begin
  2. child begin
  3. shmat OK
  4. res < 0  error = 13
  5. shmat OK
  6. res < 0  error = 13
复制代码

求职 : 机器学习
论坛徽章:
79
2015年亚洲杯纪念徽章
日期:2015-05-06 19:18:572015七夕节徽章
日期:2015-08-21 11:06:172015亚冠之阿尔纳斯尔
日期:2015-09-07 09:30:232015亚冠之萨济拖拉机
日期:2015-10-21 08:26:3915-16赛季CBA联赛之浙江
日期:2015-12-30 09:59:1815-16赛季CBA联赛之浙江
日期:2016-01-10 12:35:21技术图书徽章
日期:2016-01-15 11:07:2015-16赛季CBA联赛之新疆
日期:2016-02-24 13:46:0215-16赛季CBA联赛之吉林
日期:2016-06-26 01:07:172015-2016NBA季后赛纪念章
日期:2016-06-28 17:44:45黑曼巴
日期:2016-06-28 17:44:4515-16赛季CBA联赛之浙江
日期:2017-07-18 13:41:54
8 [报告]
发表于 2015-03-02 18:19 |只看该作者
本帖最后由 zsszss0000 于 2015-03-02 18:26 编辑

error是个常数,
  1. perror("asdfasdf");
复制代码

得到的结果是
  1. asdfasdf: Permission denied
复制代码
所以出错的原因的确是权限问题。回复 7# cdsfiui


   

论坛徽章:
2
2015年迎新春徽章
日期:2015-03-04 10:16:532015元宵节徽章
日期:2015-03-06 15:53:22
9 [报告]
发表于 2015-03-02 18:49 |只看该作者
zsszss0000 发表于 2015-03-02 18:19
error是个常数,。
得到的结果是所以出错的原因的确是权限问题。回复 7# cdsfiui


难道说,普通用户的进程不能使用共享内存? 要使用的话,需要做什么特殊的操作或者有什么调用呢?

论坛徽章:
0
10 [报告]
发表于 2015-03-03 02:02 |只看该作者
不是很清楚,帮不上什么
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

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

清除 Cookies - ChinaUnix - Archiver - WAP - TOP