2011-04-28 187 views
4

什麼是「__printflike__修飾符」?這個詞是什麼意思?__printflike__修飾符

+0

你看到什麼情況下它? (和你使用的是什麼編譯器?) – 2011-04-28 21:30:51

+0

gcc版本4.2.1在unix上。我對這個術語一無所知,並且想要理解它的非常基本的含義。 – hari 2011-04-28 21:36:40

+1

GCC不使用'__printflike__'標識符。它使用語法'__attribute __((format(printf,n,m)))',並且至少有3.3版本。如果它存在於你的代碼中,你應該發佈一段你看到的代碼片段,這樣我們可以幫助你更多。 – 2011-04-28 21:42:18

回答

6

猜測它告訴編譯器你正在使用一個函數接受形式爲[anything, ] format, ...的參數,其中format, ...部分看起來像printf的參數。 __printflike__屬性允許編譯器根據字符串格式測試參數列表中的類型。當您編寫像log(format, ...)這樣的函數並使用vsprintf將格式化工作從字符串發送到某些特殊的日誌接口之前,將它從屬於常用的標準庫函數時,會出現這種情況。

如果您使用的GCC那麼它可能是一個#define是在您的項目是這樣的:

#define __printflike__ __attribute__((format(printf, 1, 2))) 

1, 2意味着format, ...出現在位置1和2

+0

正是我所期待的!謝謝。 – hari 2011-04-28 22:04:17

1

大概告訴編譯器的相應的功能有printf-like語義。

這可以使編譯器在編譯時發出警告,當格式字符串中的修飾符與傳遞參數的類型或計數不一致時。

有沒有其他的方式,編譯器可以擁有的知識告訴你,%u

我問了反向問題主叫printfsprintffprintf等格式時爲int權前幾個月:Are printf/sprintf compiler warnings a conceptual break?

4

我有一個函數在我的錯誤報告庫中喜歡頭部聲明:

extern void err_logmsg(FILE *fp, int flags, int estat, const char *format, ...) 
         PRINTFLIKE(4,5); 

PRINTFLIKE是大寫字母,因此我可以在不使用GCC時將其定義爲無。這個用法表示前三個參數沒什麼特別,但第四個參數是一個格式字符串,與printf()使用的格式字符串(實際上,它在內部傳遞給vfprintf())以及與之對應的參數(使用格式字符串格式化)從第五個參數開始。

這意味着,如果I型:

err_logmsg(stdout, ERR_ABORT, 1, "%s: %d\n", errno, strerror(errno)); 

我會因爲errnointstrerror(errno)返回一個指向字符串得到一個編譯錯誤。我可以通過更改格式字符串或第五個和第六個參數來修復錯誤。 (ERR_ABORT是定義在同一個標​​頭中的一組標誌,聲明err_logmsg()。)

PRINTFLIKE宏中有兩個數字,因爲格式字符串和格式字符串使用的第一個參數之間可能有其他參數。例如,另一種功能可能是:

extern void err_writer(FILE *fp, const char *format, int flags, int estat, ...) 
         PRINTFLIKE(2,5); 

這告訴編譯器格式字符串是第二個參數,但是即得到格式化還是相應的參數出現在開始的第五個參數。

此代碼的頭文件包含行:

#ifdef __GNUC__ 
#define PRINTFLIKE(n,m) __attribute__((format(printf,n,m))) 
#define NORETURN()  __attribute__((noreturn)) 
#else 
#define PRINTFLIKE(n,m) /* If only */ 
#define NORETURN()  /* If only */ 
#endif /* __GNUC__ */ 
+0

感謝洛特... – hari 2011-04-28 22:03:20