2011-06-27 71 views
1

我遇到了一些我想要高效解決的問題,也許你們中的一些人也會從中學習。 我犯了一個錯誤,因爲我debbuged使用printf(或在我的情況下可能std :: cout)我的應用程序。 它進展順利,我刪除了我的錯誤,並遇到了其他問題。 現在我正處於一個階段,我希望我的調試輸出消失,但我找不到它了。 由於許多非調試打印,搜索文本並沒有提出它並且是無望的。 此外,我沒有打印超過一個變量值,所以我不知道它的名字,我也不能搜索這個特定的值,因爲它不在源代碼中。查找調試printf將其刪除

我記得一些整潔的linux命令,它記錄它包裝的應用程序中的所有系統調用。 是否可以使用此工具查找調試打印發生的行? (我會使用這個,因爲我的輸出的90%是這個調試打印,所以我想我應該很快找到它)

當然,如果你知道更好的方法來解決這個問題,歡迎你發佈你的解決方案。

感謝

編輯 如不想在每一個誰通知:我使用的版本控制註釋:我已經使用SVN。 不幸的是,我不知道什麼時候輸入了調試消息。最糟糕的情況可能是我的初始提交已經包含它。如果 它是一個調試行在所有這些其他之間。

要大家誰告訴我/想我是愚蠢的做這些事情:那麼這一個我只注意到我在這個崗位類型;)

但讓我說,這個我一切都歸結爲狀態我以前的懶惰,所以讓這成爲你們所有人的榜樣,以後的懶惰會帶來更多的工作。 我只需要一個調試打印,所以我決定以骯髒的方式對其進行編碼。如果它更多,我可能會用更好的一個。

解決

最後我發現,有一些運氣。 這是一個std :: cout,它隱藏在代碼更深的地方(其中只有少數包含全部是系統庫的基類之一)。 我嘗試了grep方法,使用一個-F1來查看任何註釋,並且在grep完成時有幸在屏幕上顯示有問題的行。

+1

使用版本控制避免將來的問題? –

+1

也許你可以通過你的版本控制系統上的日誌回顧一下,找出調試發生的地方,並在那段時間做一個差異? –

+0

'grep「std :: cout」* -r | grep text' – karlphillip

回答

4

如果這是一個printf - 做一個宏,將調用printf添加到它的文件名和行號(這些是__FILE____LINE__)。只需將宏命名爲printf,然後撥打::printf即可獲取原始功能。

如果它是cout - 有點棘手,但您可以嘗試在那裏放置斷點並查看它的調用方式,最終會找到它。

下一次 - 總是使用專用的調試打印函數或包裝宏,這些宏可以通過單個編譯器開關輕鬆地與其餘代碼分離。

+0

好的,我會給這個一個鏡頭,並希望它的一個printf;) – Nobody

+0

@無人 - 請確保你在所有的代碼庫中包含這個宏,我希望你有一個單一的.H文件隨處可見:-) – littleadv

+0

這就是我現在的問題。但是我經歷過的最多的機會是它是一個std :: cout。 – Nobody

1

本頁面:http://sclogger.sourceforge.net/ 有一個程序可以讓你記錄系統調用。也許這就是你要找的。

未來,您可以做如下的事情。

#ifdef DEBUG 
std::cout << "Debugging message" << std::endl; 
#endif 

您可以控制是否在編譯時定義符號DEBUG。

+1

該網頁包含「該模塊僅適用於2.4.x Linux內核」的信息。這些日子的價值有限。 –

1

你想要更好的方法:

使用版本控制!然後將您的工作副本與基本版本進行比較;假設你還沒有做過無數的改變,應該很容易找到你的printf

UPDATE

如果你不知道你的修訂添加這種行爲,後來乾脆做一個二進制搜索。在版本1000(例如),然後是500,然後是750,然後是625等等運行您的應用程序。這與定位引入錯誤的時間點的方法非常相似。

1

如果你在linux系統中,你可以使用grep解析整個代碼樹,並讓你顯示每一個命令「std :: cout」。如果你只打印一個值,你應該看到相關的行很快。

或者你可以找一個正則表達式,如果你知道有沒有「在你的調試行:s/std\:\:cout\b[^"]*std\:\:endl/

爲了檢測SVN的變化:使用svn-bisect

3

你不需要沒有花哨的版本控制系統!所有你需要的是自律,以紀念所有的(是的,所有)調試輸出與/ * REMOVE ME * /註釋。

只花了我30年的學習這一點。

+0

+1:這是非常好的建議。 –

+0

+1:程序員總是會討厭做額外的工作。 – Nobody

+0

爲了有助於紀律:'#define REMOVE_ME',所以你可以寫'REMOVE_ME printf(「%d」,x);'。如果它不是註釋,那麼可以將其更改爲編譯器將拒絕的某個符號。 – MSalters

0

作爲一個經驗法則,我一直有這樣的事情:

#ifdef DEBUG 
int dbg_printf(char * format, ...) { 

    va_list ap; 
    va_start(ap, format); 

    vsnprintf(my_printf_buf, my_printf_bufsize, format, ap); 
    uart3_putstr(my_printf_buf); // debug connector 

    va_end(ap); 

    return 0; 
} 
#else 
#define dbg_printf(format, ...) 
#endif 

的好處是,當你不進行調試,所有這些dbg_printf()你有你的代碼通過預處理器被吃掉,不要膨脹你的代碼。