realloc C 函数的可能包装函数有什么错误?

What's the bug with a possible wrapper function of realloc C function?

我想知道 realloc C 函数的以下可能包装函数中可能存在的错误:

void reallocX(void** ptr, size_t size)
{
    void *new_ptr = realloc(*ptr, size);
    if (new_ptr != NULL)
    {
        if (new_ptr != *ptr)
        {
            *ptr = new_ptr;
        }
    }
    else
    {
        printf( "Help! realloc returned NULL!\n");
        exit( EXIT_FAILURE);
    }
}

.

我知道它基于malloc C函数的可能包装函数,即:

void *
mallocX (size_t nbytes)
{
  void *ptr;
  ptr = malloc (nbytes);
  if (ptr == NULL) {
    printf( "Help! malloc returned NULL!\n");
    exit (EXIT_FAILURE);
  }
  return ptr;
}

。这个 malloc C 函数包装函数是基于 this webpage 的 "mallocc" C 函数。

感谢您的帮助。

来自 realloc 的空指针 return 值可能表示:

  1. 函数没有分配存储空间。
  2. 大小参数为零且内存已释放。

您的代码涵盖了第一种可能性,但没有涵盖第二种可能性。 null return 值可以是有效的,表示内存块的释放已成功完成。在这些情况下发出错误信号是一个错误。

注意这适用于 C90 C++98

如评论中所述,传递大小参数 0 是 C99/C11 C++11 中特定的实现。

至少有一个错误;这一行:

    if (new_ptr != *ptr)

调用未定义的行为。在 realloc 成功后禁止使用旧指针,尤其是与新指针的比较。您需要无条件地进行赋值。

此外,虽然这不是内部错误,但外部 API 设计不当且容易出错。调用者指针的类型通常不是 void *,而是其他一些指针类型,如 char *struct foo *,您将让用户执行:

reallocX((void **)&myptr, size);

这会导致您的函数通过别名违规调用未定义的行为(至少;如果 size/representation 中不同的指针类型不同,也可能是越界写入),因为它正在访问 void * 对象的地址不指向 void * 对象,而是指向其他类型的指针对象。

这些包装纸是有害的,需要拒绝。没办法做到 right/safely.