如何在字段中存储格式字符串,并避免格式非线性警告? [英] How can I store format string in a field and avoid the format-nonliteral warning as well?

查看:420
本文介绍了如何在字段中存储格式字符串,并避免格式非线性警告?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我知道你可以放置 __ attribute __((__ format__(__printf__,2,0))),以避免clang警告format string is not a string literalif一个函数需要将格式化字符串传递给vsnprintf。然而,在我的情况下,格式字符串保存为字段,用字面量初始化。类似这样:

  class Worker {
const char * format;
worker(const char * f):format(f){...}

void go(){
...
vsnprintf ..,格式,..);
...
}
}

您可以使用 #pragma clang诊断忽略-Wformat-nonliteral

code>或将替换为 GCC

  #include< cstdio> 
#include< cstdarg>

using namespace std;

class Worker {
const char * format;
Worker(const char * f):format(f){}

void go(int j,...){
char data [256]
va_list args;
va_start(args,j);
#pragma clang diagnostic push
#pragma clang diagnostic ignored-Wformat-nonliteral
vsnprintf(data,sizeof(data),format,args);
#pragma clang diagnostic pop
va_end(args);
fputs(data,stderr);
}
};

push pop 限制诊断处理中更改的范围,以便只有一行可以免除警告。有关详细信息,请参见 GNU诊断编译指示 Clang诊断pragmas



上面的代码用下面的代码编译:

  $ clang -O3 -g -std = c ++ 11 -Wall -Wextra -Werror -Wformat-nonliteral -c clang.cc 

GCC失败。将 clang 替换为 GCC ,然后在GCC和Clang下整理。



在Mac OS X 10.9.2上测试Mavericks:




  • GCC( g ++ )4.8.2

  • Clang( clang )Apple LLVM版本5.1(clang-503.0.38)基于LLVM 3.4svn)'。


I know you can place __attribute__((__format__ (__printf__, 2, 0))) to avoid the clang warning of "format string is not a string literal" if a function needs to pass a format string into vsnprintf. However in my case, the format string is saved as a field which is initialized with a literal. Something like this:

class Worker {
    const char* format;
    Worker(const char* f): format(f) {...}

    void go() {
        ...
        vsnprintf(..,..,format,..);
        ...
    }
}

How can I avoid the warning?

解决方案

You can use #pragma clang diagnostic ignored "-Wformat-nonliteral" or replace clang with GCC:

#include <cstdio>
#include <cstdarg>

using namespace std;

class Worker {
    const char* format;
    Worker(const char* f): format(f) { }

    void go(int j, ...) {
        char data[256];
        va_list args;
        va_start(args, j);
        #pragma clang diagnostic push
        #pragma clang diagnostic ignored "-Wformat-nonliteral"
        vsnprintf(data, sizeof(data), format, args);
        #pragma clang diagnostic pop
        va_end(args);
        fputs(data, stderr);
    }
};

The push and pop limit the scope of the changes in diagnostic handling so that only the one line is exempted from the warning. For more information, see GNU diagnostic pragmas and Clang diagnostic pragmas.

The code above compiles cleanly with:

$ clang -O3 -g -std=c++11 -Wall -Wextra -Werror -Wformat-nonliteral -c clang.cc

It fails noisily with GCC. Replace the clang with GCC and it compiles cleanly under both GCC and Clang.

Tested on Mac OS X 10.9.2 Mavericks with:

  • GCC (g++) 4.8.2
  • Clang (clang) 'Apple LLVM version 5.1 (clang-503.0.38) (based on LLVM 3.4svn)'.

这篇关于如何在字段中存储格式字符串,并避免格式非线性警告?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆