简体   繁体   English

realloc:分段错误

[英]realloc: Segmentation fault

Take the following code,which is in ac : 请使用以下代码,该代码位于ac

struct header {
    char **name;
};
int main(void)
{
    int i=0;
    char **p;
    struct header h;
    char tmp[10];
    memset(&h, 0, sizeof(h));

    for(i=1;i<10;i++){
        sprintf(tmp, "name%d", i); 
        p = realloc(h.name, sizeof(char*)*i);
        printf("h->name=%p, p=%p\n", h.name, p); 
        h.name = p;
        h.name[i-1] = malloc(100);
        strncpy(h.name+i-1, tmp, strlen(tmp));
        printf("h->name=%s\n", h.name+i-1);
    }   
    return 0;
}

after i gcc ac and ./a.out ,following error happends: Segmentation fault I have no any idea about this,what exactly this happen? 在我的gcc ac./a.out ,发生以下错误: Segmentation fault我对此一无所知,究竟发生了什么?

EDIT1: found the qustion! EDIT1:找到了qustion! strncpy(h.name+i-1, tmp, strlen(tmp)) should strncpy(h.name[i - 1], tmp, strlen(tmp) + 1) and this qustion can be found through gcc warnings:/usr/include/string.h:131:14: note: expected 'char * __restrict__' but argument is of type 'char **' ,so silly! strncpy(h.name+i-1, tmp, strlen(tmp))应该strncpy(h.name[i - 1], tmp, strlen(tmp) + 1)并且可以通过gcc warnings:/usr/include/string.h:131:14: note: expected 'char * __restrict__' but argument is of type 'char **'找到此qustion gcc warnings:/usr/include/string.h:131:14: note: expected 'char * __restrict__' but argument is of type 'char **' ,太傻了! thanks to everyone! 谢谢大家!

strncpy(h.name+i-1, tmp, strlen(tmp)); doesn't null terminate the destination string. 不为null终止目标字符串。 It may be that the next printf() crashes trying to print it. 可能是下一个printf()崩溃试图打印它。

I suspect you're compiling on a 64 bit system, and don't have: 我怀疑你是在64位系统上进行编译,而且没有:

#include <stdlib.h>

at the top of your file. 在您的文件的顶部。 You should get a warning about this when you compile: 编译时应该收到关于此的警告:

incompatible implicit declaration of built-in function 'malloc' 内置函数'malloc'的不兼容隐式声明

As Michael Burr points out, you're also not terminating the string correctly. 正如Michael Burr指出的那样,你也没有正确地终止字符串。

You should be able to find out where it is crashing by compiling with -g and running it through a debugger (eg gdb). 您应该能够通过使用-g进行编译并通过调试器(例如gdb)运行它来找出崩溃的位置。

The problem is that your strncpy is only strlen(tmp) so if temp is name5, strlen(tmp) == 5, which doesn't copy the NULL that your sprintf put on. 问题是你的strncpy只是strlen(tmp)所以如果temp是name5,strlen(tmp)== 5,它不会复制你的sprintf所放的NULL。 You need to do strlen(tmp)+1 to copy in the NULL. 你需要在NULL中复制strlen(tmp)+1。

http://linux.die.net/man/3/strncpy http://linux.die.net/man/3/strncpy

Also, it's odd that h.name is a double pointer to char. 另外,奇怪的是h.name是char的双指针。 If it should be a string, it should just be a char *. 如果它应该是一个字符串,它应该只是一个char *。 It is then weird that you're only mallocing space for your array of single pointers to one entry. 然后奇怪的是,你只需要为一个条目的单指针数组提供空间。

'\\0' of a string is not the whole thing.although you need 字符串的'\\ 0'不是全部。尽管你需要

strlen(tmp)+1 

but the main error is that you didn't dereference your char** pointer like this: 但主要的错误是你没有取消引用你的char **指针,如下所示:

strncpy(*(h.name+i-1), tmp, strlen(tmp)+1);
printf("h->name=%s\n", *(h.name+i-1));

this below will work, and I have tested it by my gcc: 以下这个将起作用,我已经通过我的gcc进行了测试:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

struct header {
char **name;
};

int main(void)
{
    int i=0;
    char **p;
    struct header h;
    char tmp[10];
    memset(&h, 0, sizeof(h));

    for(i=1;i<10;i++){
        sprintf(tmp, "name%d", i);
        //printf("tmp:%s\n",tmp);
        p = realloc(h.name, sizeof(char*)*i);
        printf("h->name=%p, p=%p\n", h.name, p);
        if(p==NULL) {
            printf("realloc failed.\n");
            return -1;
        }
        h.name = p;
        h.name[i-1] = (char *)malloc(100);
        strncpy(*(h.name+i-1), tmp, strlen(tmp)+1);
        printf("h->name=%s\n", *(h.name+i-1));
    }   
    return 0;
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM