【问题标题】:C Pointer Assignment: wrong address and segmentation faultC指针分配:错误的地址和分段错误
【发布时间】:2012-06-15 15:33:44
【问题描述】:

我在这里遇到了一个非常奇怪的问题,希望有人可以帮助我。这就是代码。

Node *fct(Node *list)
{
  Node *node;
  node = list;
  ...
}

通常一切都运行顺利,但在某些随机情况下,我会遇到分段错误。我用 GDB 调试。通常列表和节点的地址都是 0x80d4000,但是当 Segfault 发生时,节点的地址 = 0x400。 (列表仍然是 0x80d4000)。
我真的不知道这可能会出错,有什么想法吗?

【问题讨论】:

  • 也许您在其他地方损坏了内存。我们需要更多代码,给定的片段没有任何问题。
  • 很多想法,但没有更多代码,无法知道哪个想法对您的情况真正有用。
  • 不是这里的代码有问题,而是调用 fct() 函数的人传递了无效数据。 (很可能它试图传递一个 NULL 指针的成员的地址)
  • 检查 valgrind (valgrind.org) memchecker 工具是否可以帮助您更多
  • 因为我必须实现自己的 malloc,可能有 1000 种可能性我可以破坏内存和许多代码行在这里发布:( 我想我只需要继续调试。谢谢反正

标签: c pointers segmentation-fault fault memory-address


【解决方案1】:

这不是足够的代码来确定,但我怀疑在某个地方,您传递了地址的副本(指针)并在 COPY 上进行了修改(如 malloc);而不是传递此地址的地址(指针上的指针),因此您实际上修改的是指针而不是其副本之一。

一个例子来说明我在说什么:

int dostuff(char* str)
{
    str = malloc(sizeof(char));
    str[0] = 0x42;
    return 1; // size of string.
}

int main(int argc, char** argv)
{
    char* mystr = NULL;
    unsigned int strlength = 0;
    strlength = dostuff(mystr);
    printf("%s\n", mystr);  // Segfaults here: mystr == NULL.
    free(mystr);
    return 0;
}

这就是正在发生的事情:

  1. 您创建一个设置为 NULL 的新 char 指针(例如,如果您想重新分配则更好)。
  2. 您将其值 (NULL) 传递给 dostuff。该函数复制此值(具有 char* 类型),并修改此副本。
  3. printf 访问 mystr 进行打印,在尝试从 NULL[0] (0) 读取时,会出现段错误。

main 的其余部分当然不会执行。

这就是为什么有人会掉进那个坑的原因:通常,当你使用某个指针和一个函数对其进行一些修改时,你修改的是它的内容,而不是它的地址。当你修改它的地址时,你几乎总是(除了这种情况)有修改它的函数来返回它的新地址。比如address = malloc(size)

另一方面,如果您想设置一个 POINTER(显然不是内容),您需要将其地址的副本传递给函数。这是上面代码的工作版本:

int dostuff(char** str)
{
    (*str) = malloc(sizeof(char));
    (*str)[0] = 0x42;
    return 1; // size of string.
}

int main(int argc, char** argv)
{
    char* mystr = NULL;
    unsigned int strlength = 0;
    strlength = dostuff(&mystr);
    printf("%s\n", mystr);  // Now works: mystr is allocated.
    free(mystr);
    return 0;
}

所以请记住:如果有疑问,请返回指针并获取其他变量的地址(此处为strlength)。如果不可能,请对您正在操作的数据的实际类型非常谨慎,并在修改后仔细检查您的地址。

希望对你有帮助。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2016-01-02
    • 2013-09-18
    • 2016-02-24
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多