2017-08-14 105 views
3

我的影片定義爲斷言宏:多個錯誤斷言宏

#define likely(cond) (__builtin_expect((cond), 1)) 
#define unlikely(cond) (__builtin_expect(!!(cond), 0)) 

static void assert_fail(const char *__assertion, const char *__file, 
          unsigned int __line, const char *__function) { 
    fprintf(stderr, "\nASSERT failed %s:%d %s()\n%s\n", __file, __line, __function, __assertion); 

    void *array[50]; 
    size_t size = backtrace(array, 50);  // Fill out array of pointers to stack entries 
    backtrace_symbols_fd(&array[1], size, STDERR_FILENO); 
    exit(1); 
} 

#define assert(expr) (likely(expr) ? (void) (0) : \ 
         assert_fail(#expr, __FILE__, __LINE__, __func__)) 

當你做出一個斷言狀態裏一個簡單的錯誤,如錯誤的變量名,除了工作正常,:

assert(size > 0); 

它打印出一個非常明智的錯誤,然後是5個註釋(包括重複),這使得它更難以閱讀。有沒有解決這個問題的方法可以讓你更容易閱讀?核心問題似乎是使用宏,但我看不到如何避免在這裏,給定使用__FILE__,__LINE__

禁用「注:每個未申報的標識符只報告一次每個功能」將縮短一半,如果這是可能的(雖然我無法找到任何方式做到這一點)

abc.c: In function 'init': 
abc.c:53:12: error: 'size' undeclared (first use in this function) 
    assert(size > 0); 
      ^
include/assert.h:21:41: note: in definition of macro 'likely' 
#define likely(cond) (__builtin_expect((cond), 1)) 
             ^
abc.c:53:5: note: in expansion of macro 'assert' 
    assert(size > 0); 
    ^
abc.c:53:12: note: each undeclared identifier is reported only once for each function it appears in 
    assert(size > 0); 
      ^
include/assert.h:21:41: note: in definition of macro 'likely' 
#define likely(cond) (__builtin_expect((cond), 1)) 
             ^
abc.c:53:5: note: in expansion of macro 'assert' 
    assert(size > 0); 
    ^
+0

第一個錯誤信息就足以對此進行診斷。就像往常一樣修復它 –

+0

我從gcc切換到鏗鏘聲,大多修復它。在這種情況下,錯誤消息看起來更好,並且據稱還有很多其他消息。 – Martin

回答

3

作爲一般規則,在處理編譯器錯誤時,解決您發現的第一個錯誤,然後重新編譯。這樣你就不會浪費時間追逐級聯錯誤。

在這種特殊情況下,您會注意到您有一條「錯誤」行,後面跟着幾條「註釋」行。無論何時您看到「筆記」消息,它都會提供有關最新「錯誤」或「警告消息」的其他信息。你不應該壓制像這樣的消息(我不相信你可以),因爲它們可以爲你提供有關錯誤真正根源的有價值的信息。

這裏給出了這些「音符」的消息是有用的一個例子:

#include <stdio.h> 

void f1(double x); 

int main() 
{ 
    f1(3); 
    return 0; 
} 


void f1(int x) 
{ 
    printf("x=%d\n", x); 
} 

在這段代碼的f1聲明的定義不匹配。編譯器生成以下消息:

x1.c:12:6: error: conflicting types for ‘f1’ 
void f1(int x) 
    ^
x1.c:3:6: note: previous declaration of ‘f1’ was here 
void f1(double x); 

的「錯誤」的消息告訴您,在第12行的定義不相符的聲明,但它並沒有說什麼聲明,它與衝突。這出現在下面的「註釋」消息中。在大型項目中,如果沒有「筆記」消息,您可能無法找到衝突。

+0

瞭解,這裏特別麻煩,因爲有多層。能夠抑制這個宏的註釋是有用的。 尤其是當它重複多個註釋來告訴我每個未聲明的標識符只報告一次。 展開內聯可能的宏將其從6降低到4。 – Martin

0

如果表達式的值爲TRUE,斷言()什麼都不做。如果expression的計算結果爲FALSE,則assert()會在stderr上顯示錯誤消息(標準錯誤流以顯示錯誤消息和診斷信息)並中止程序執行。

+0

歡迎來到Stack Overflow。請儘快閱讀[關於]和[回答]頁面。雖然您提供的信息是準確的,但它並不回答所問的問題。因此,這沒有幫助。我建議刪除這個。 –

+0

我是一個新的程序員..... –

+0

我們都曾經,曾經。對於我們中的一些人來說,那種「曾幾何時」是很久以前,在互聯網或全球網絡之前的日子裏。 –