我在C.中创建了一个简单的记录器库.我有三个文件
我的示例文件:
> example.c
库文件:
> loglib.h
> loglib.c
我的主记录器功能称为logme.我将不同的宏定义为包装器以指示不同的日志级别:
例如
>警告
>错误
>等..
在example.c中我调用宏:
int int_arg = 55;
WARN(1, "Warn message with level 1");
WARN(1, "Warn message with level %d", int_arg);
WARN宏在loglib.h中定义:
#define WARN(LEVEL, ...) \
logme(LEVEL, 8, " <%s:%d> inside %s() -- "__VA_ARGS__, __FILE__, __LINE__, __func__);
最后这里是logme函数:
void slog(int level, int flag, const char *msg, ...)
{
char string[10000];
bzero(string, sizeof(string));
va_list args;
va_start(args, msg);
vsprintf(string, msg, args);
va_end(args);
// .. do other things
}
当我运行示例文件时,这就是我得到的:
inside main() — Warn message with level 1
Segmentation fault (core dumped)
当我使用格式化字符串调用WARN时,我会出现分段错误.
分段错误出现在vsprintf(string,msg,args);
我的宏有问题吗?
这是我的lib的make文件:
CFLAGS = -g -O2 -Wall -lpthread
LIB = -lrt
OBJS = loglib.o
LIBINSTALL = /usr/local/lib
HEADINSTALL = /usr/local/include
.c.o:
$(CC) $(CFLAGS) -c $< $(LIB)
libslog.a: $(OBJS)
$(AR) rcs liblog.a $(OBJS)
@echo [-] Syncing static library
sync
install:
@test -d $(LIBINSTALL) || mkdir $(LIBINSTALL)
@test -d $(HEADINSTALL) || mkdir $(HEADINSTALL)
@install -m 0664 liblog.a $(LIBINSTALL)/
@install -m 0664 loglib.h $(HEADINSTALL)/
@echo [-] Done
loglib.o: loglib.h
.PHONY: clean
clean:
$(RM) liblog.a $(OBJS)
最佳答案 这不起作用,因为您在此处尝试字符串连接__VA_ARGS__:
#define WARN(LEVEL, ...) \
logme(LEVEL, 8, " <%s:%d> inside %s() -- "__VA_ARGS__, __FILE__, __LINE__, __func__);
这会弄乱你的参数序列:__ FILE__不会与<%s等一起使用.你必须重新定义你的WARN()宏,以便__VA_ARGS__是最后一个.如果要预先添加所有信息,则必须编写适当的可变参数函数.请注意,__ func__不是字符串文字,它引用相应的字符串.