选择合适的错误报告机制:如何在编译时更改宏?

时间:2016-03-17 15:50:53

标签: c macros exit

我希望我的程序从每个不正确的退出报告不同的退出代码,所以像

fprintf(stderr, "bad foo in bar (%d)", -1);
exit(-1);
...
fprintf(stderr, "bad baz in qux (%d)", -2);
exit(-2);
...
fprintf(stderr, "bad boop in bing (%d)", -3);
exit(-3);
可以调用每个地方出口的

等等。由于保持位数可能是一个很大的痛苦,我想使用一个宏:

MY_ERR("...")

扩展为

do{ fprintf("...""(%d)", --EXITCODE);
    exit(EXITCODE); } while(0);

所以问题就变成了,什么是EXITCODE?如果它是正常的C变量,那么它只在运行时递减,并且它会立即退出,因此每个错误都不会有唯一的数字,并且数字将始终为-1(如果EXITCODE从0开始) )。但如果它是一个#define d宏,那么我们就不能减少它。

有没有办法做我想要的?我想我可以使用__LINE__,但这不会影响多个文件。我可以将__FILE____LINE__组合使用,但这不能成为exit的代码。

2 个答案:

答案 0 :(得分:0)

显而易见的解决方案是创建一个包含所有错误代码的表。枚举或const数组。无论如何,你需要一些关于这些魔法数字含义的文档。

例如:

errors.h

typedef enum
{
  ERR_BAD_FOO,
  ERR_BAD_BAZ,
  ERR_BAD_BOOP,
  ERRORS_N
} err_t;

void error_then_exit (err_t error);

errors.c

#include "errors.h"

void error_then_exit (err_t error)
{
  const char* ERR_STR [] =
  {
    "bad foo in bar",
    "bad baz in qux",
    "bad boop in bing"
  };

  _Static_assert(ERRORS_N == sizeof(ERR_STR)/sizeof(*ERR_STR), 
                 "Errors in the error handler!");

  int code = -(int)error;

  fprintf(stderr, "%s (%d)\n", ERR_STR[error], code);
  exit(code);
}

用法:

#include "errors.h"

error_then_exit (ERR_BAD_FOO);

答案 1 :(得分:0)

实际上,只有128个退出代码(0-127)可以用作退出代码128-255被shell重载,以便通过信号终止程序。在一个中型程序中,这远远不足以为每个exit调用一个不同的退出代码。这也不是用户想要的:毕竟,用户从未阅读过您的源代码。用户想要知道为什么程序终止,而不是 终止。

我的建议是为你的程序失败制定一套粗略的条件并为每个程序分配一个错误代码。您可以查看FreeBSD's set获取灵感。请考虑退出状态仅用于脚本以确定要采取的操作。它必须足够粗糙,不要成为解码的痛苦,但要足够精细才能有用。

将所有其他信息(例如发生故障的源文件)放入错误消息中。请详细说明并写下错误消息,以便用户有机会了解他可以采取哪些措施来解决问题。