gpt4 book ai didi

c - 如何正确处理 C 中的 malloc 失败,尤其是当有多个 malloc 时?

转载 作者:IT王子 更新时间:2023-10-28 23:28:52 29 4
gpt4 key购买 nike

假设这是我的代码的一部分:

 int foo()
{
char *p, *q ;
if((p = malloc(BUFSIZ)) == NULL) {
return ERROR_CODE;
}
if((q = malloc(BUFSIZ)) == NULL) {
free(p)
return ERROR_CODE;
}
/* Do some other work... */

free(p);
free(q);
}

由于第一个 malloc 可能成功但第二个失败,我在第二个“错误处理程序”中使用 free(p)。但是如果有更多的malloc,如果我想修改代码(调整它们的顺序,添加或删除一些malloc)怎么办?

我知道在 C++ 中有诸如 RAII 和异常安全之类的东西。但总的来说,在 C 中处理 malloc 失败的正确方法是什么? (也许使用一些 goto?)

最佳答案

您的代码很好,但对于很多变量,我更喜欢:

int
foo()
{
char *p = NULL;
char *q = NULL;
int ret = 0;

if (NULL == (p = malloc(BUFSIZ)))
{
ret = ERROR_CODE;
goto error;
}

// possibly do something here

if (NULL == (q = malloc(BUFSIZ)))
{
ret = ERROR_CODE;
goto error;
}

// insert similar repetitions

// hopefully do something here

error:
free (p);
free (q);
return ret;
}

请注意,释放 NULL 被定义为无操作。

这避免了 n 变量的 n 级缩进。您可以类似地清理文件句柄等(尽管您必须在 close() 周围设置一个条件)。

现在,如果您知道可以一次全部分配,那么 dasblinkenlight 有一个很好的答案,但这里有另一种方法:

int
foo()
{
int ret = 0;
char *p = malloc(BUFSIZ);
char *q = malloc(BUFSIZ);
char *r = malloc(BUFSIZ);
if (!p || !q || !r)
{
ret = ERROR_CODE;
goto exit;
}

// do something

exit:
free(p);
free(q);
free(r);
return ret;
}

最后的可能性:如果您真的想在 malloc 失败时退出程序,请考虑使用 malloptM_CHECK_ACTION 选项。这会检查 malloc() 错误,并调用 abort(),可能会打印有用的消息。

来自手册页:

NAME

mallopt - set memory allocation parameters

SYNOPSIS

  #include <malloc.h>

int mallopt(int param, int value);

DESCRIPTION

The mallopt() function adjusts parameters that control the behavior of the memory-allocation functions (see malloc(3)). The param argument specifies the parameter to be modified, and value specifies the new value for that parameter.

The following values can be specified for param:

M_CHECK_ACTION

Setting this parameter controls how glibc responds when various kinds of programming errors are detected (e.g., freeing the same pointer twice). The 3 least significant bits (2, 1, and 0) of the value assigned to this parameter determine the glibc behavior, as follows:

Bit 0: If this bit is set, then print a one-line message on stderr that provides details about the error. The message starts with the string "*** glibc detected ***", followed by the program name, the name of the memory-allocation function in which the error was detected, a brief description of the error, and the memory address where the error was detected.

Bit 1: If this bit is set, then, after printing any error message specified by bit 0, the program is terminated by calling abort(3). In glibc versions since 2.4, if bit 0 is also set, then, between printing the error message and aborting, the program also prints a stack trace in the manner of backtrace(3), and prints the process's memory mapping in the style of /proc/[pid]/maps (see proc(5)).

Bit 2: (since glibc 2.4) This bit has an effect only if bit 0 is also set. If this bit is set, then the one-line message describing the error is simplified to contain just the name of the function where the error was detected and the brief description of the error.

关于c - 如何正确处理 C 中的 malloc 失败,尤其是当有多个 malloc 时?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27451220/

29 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com