2013-02-23 58 views
0

....嗨,大家好,我总是在运行我的代码时出现“分段错误”。我知道这个错误发生在写入文件时出现问题(我想共享内存也是如此),我知道错误来自于for循环,我尝试了所有解决这个错误的方法,但都失败了(我甚至删除了for循环,只输入* s ='A')。任何帮助请。给共享内存段写信时出现问题

#include <stdio.h> 
#include <sys/types.h> 
#include <sys/ipc.h> 
#include <sys/shm.h> 
#include <stdlib.h> 

main() 
{ 
    //Shared memory parameters 
    int shmid ; 
    int shmsize = 14; 
    key_t key = 2121; 
    char *shm, *s; 
    //Create SMS 
    if ((shmid = shmget (key , shmsize, 0666 | IPC_CREAT)) == -1) { 
     perror ("Error in Creating the SMS"); 
     abort(); 
    } 
    //Attatching the sms to the address space 
    if (shm = shmat(shmid , NULL , 0) == (char *)-1) { /*<<<< 23 */ 
     perror ("Error in attatching the SMS"); 
     abort(); 
    } 
    int i ; 
    s = shm; 
    for(i = 0 ; i <= 63 ; i++) 
     *s++ = (char)i; 
     *s = NULL; /*<<<< 33 what's the problem */ 
} 

而且我得到了两个23和33

回答

1

你应该听编译器警告(你应该得到一个预警线7警告,一有main它还有 - 如果你不't,那么你应该添加-Wall到编译器开关)。

所以在23行,它说“让指针从整数,未作类型转换” [1]:

if (shm = shmat(shmid , NULL , 0) == (char *)-1) 

这是因为你的代码行没有做什么,你认为它应该做的。如果我们把它分成不同的行,那就更清楚了,不是吗?

shm = shmat(shmid , NULL , 0) == (char *)-1; 
    if (shm) 

因此,SHM成为从shmat(...) == -1返回值”的结果是希望为零,则分配sshm,这意味着*s++试图写入地址零。 - 这绝对应该给赛格故障。

修复此通过添加括号以使分配第一发生,那么比较(如以上shmid = shmget几行) - 或分裂它像这样(我的优选方案):

shm = shmat(shmid , NULL , 0); 
    if (shm == (char *)-1) 

这条线:

    *s = NULL; //what's the problem 

是错误的,因为你要转让NULL(这是(void *)0,因而指针)到char值。通过这两种线的纠正这一点,

*s = '\0'; 
*s = 0; 

按下面的评论:你也应该照顾到您的大小共享内存覆盖要存储的内容。目前您需要14个字节,然后写入64个字节。这不会失败,但这只是因为大小会变为4096字节 - 不要在操作系统中“谎报”您所要求的内容 - 甚至是“如果你有时摆脱它......

[1]它总是有益的,如果你发布实际的警告信息,这将节省我不必编译代码找到警告...

+2

您可以添加到你的回答中:shm的大小是14,循环是63字节...... – Aubin 2013-02-23 16:33:03

+0

非常感谢,下次我会小心的。 – 2013-02-23 17:02:28