<kbd id="afajh"><form id="afajh"></form></kbd>
<strong id="afajh"><dl id="afajh"></dl></strong>
    <del id="afajh"><form id="afajh"></form></del>
        1. <th id="afajh"><progress id="afajh"></progress></th>
          <b id="afajh"><abbr id="afajh"></abbr></b>
          <th id="afajh"><progress id="afajh"></progress></th>

          printf 宏 居然有這么秀的調(diào)試技巧...

          共 2710字,需瀏覽 6分鐘

           ·

          2020-11-23 22:32

          1.

          前言

          printf調(diào)試是嵌入式調(diào)試的基本手段,而且是非常重要的手段,我認(rèn)為相比單步調(diào)試更加有用有效,特別是單片機(jī)之后跑系統(tǒng),單步調(diào)試效率更加低下了,我們?cè)诠ぷ饔龅絙ug的時(shí)候,我們第一時(shí)間就想知道那些該死的日志有沒(méi)有保存下來(lái),這樣好讓我們程序員裝逼一波把問(wèn)題解決。

          printf宏定義調(diào)試非常重要,有些日志在開發(fā)的時(shí)候才需要打開,發(fā)布的時(shí)候需要關(guān)閉,但是在代碼上又需要保留下次調(diào)試,所以我們?cè)谡{(diào)試的時(shí)候才打開調(diào)試宏定義,而且printf會(huì)占用空間,很多芯片的空間非常有限,更應(yīng)該關(guān)閉調(diào)試宏。

          下面就直接進(jìn)入正題,說(shuō)一下調(diào)試的技巧


          2.

          正文


          1 編譯器內(nèi)置宏

          先介紹幾個(gè)編譯器內(nèi)置的宏定義,這些宏定義不僅可以幫助我們完成跨平臺(tái)的源碼編寫,靈活使用也可以巧妙地幫我們輸出非常有用的調(diào)試信息。

          ANSI C標(biāo)準(zhǔn)中有幾個(gè)標(biāo)準(zhǔn)預(yù)定義宏(也是常用的):

          __LINE__:在源代碼中插入當(dāng)前源代碼行號(hào);

          __FILE__:在源文件中插入當(dāng)前源文件名;

          __DATE__:在源文件中插入當(dāng)前的編譯日期

          __TIME__:在源文件中插入當(dāng)前編譯時(shí)間;

          __STDC__:當(dāng)要求程序嚴(yán)格遵循ANSI C標(biāo)準(zhǔn)時(shí)該標(biāo)識(shí)被賦值為1;

          __cplusplus:當(dāng)編寫C++程序時(shí)該標(biāo)識(shí)符被定義。

          編譯器在進(jìn)行源碼編譯的時(shí)候,會(huì)自動(dòng)將這些宏替換為相應(yīng)內(nèi)容。


          2 最基本的用法

          打開宏的時(shí)候輸出


          關(guān)閉宏的時(shí)候輸出


          3 換個(gè)高級(jí)的用法
          ????? ? 代碼如下

          #include?

          #define?__DEBUG__

          #ifdef?__DEBUG__
          #define?DEBUG(format,...)?printf("Date:?"__DATE__",File:?"__FILE__",?Line:?%05d:?"format"\n",?__LINE__,?##__VA_ARGS__)
          #else
          #define?DEBUG(format,...)
          #endif

          int?main(int?argc,?char?**argv)?{
          ????char?str[]="Hello?World";
          ????DEBUG("%s",str);
          ????return?0;
          }


          輸出如下

          Date:?Oct??5?2018,File:?/code/main.c,?Line:?00013:?Hello?World
          sandbox>?exited?with?status?0


          在線編譯器網(wǎng)址:https://tool.lu/coderunner/


          ?4 ## __VA_ARGS__ ... 宏和可變參數(shù)

          在GNU C中,宏可以接受可變數(shù)目的參數(shù),就象函數(shù)一樣

          例如:?

          #define?pr_debug(fmt,arg...)?\?
          printk(KERN_DEBUG?fmt,?##arg)

          用可變參數(shù)宏(variadic macros)傳遞可變參數(shù)表?
          你可能很熟悉在函數(shù)中使用可變參數(shù)表,如:

          void?printf(const?char*?format,?...);

          直到最近,可變參數(shù)表還是只能應(yīng)用在真正的函數(shù)中,不能使用在宏中。

          C99編譯器標(biāo)準(zhǔn)允許你可以定義可變參數(shù)宏(variadic macros),這樣你就可以使用擁有可以變化的參數(shù)表的宏。可變參數(shù)宏就像下面這個(gè)樣子:

          #define?debug(...)?printf(__VA_ARGS__)

          缺省號(hào)代表一個(gè)可以變化的參數(shù)表。使用保留名 __VA_ARGS__ 把參數(shù)傳遞給宏。當(dāng)宏的調(diào)用展開時(shí),實(shí)際的參數(shù)就傳遞給 printf()了

          例如:?

          debug("Y?=?%d\n",?y);

          而處理器會(huì)把宏的調(diào)用替換成:?

          printf("Y?=?%d\n",?y);

          因?yàn)閐ebug()是一個(gè)可變參數(shù)宏,你能在每一次調(diào)用中傳遞不同數(shù)目的參數(shù):?

          debug("test");//?一個(gè)參數(shù)

          用GCC和C99的可變參數(shù)宏, 更方便地打印調(diào)試信息
          可變參數(shù)宏不被ANSI/ISO C++ 所正式支持。因此,你應(yīng)當(dāng)檢查你的編譯器,看它是否支持這項(xiàng)技術(shù)。?

          可變參數(shù)的宏里的'##'操作說(shuō)明帶有可變參數(shù)的宏(Macros with a Variable Number of Arguments)?

          更詳細(xì)請(qǐng)查看如下鏈接

          http://www.cnblogs.com/alexshi/archive/2012/03/09/2388453.html


          ?5 舉個(gè)栗子-Linux內(nèi)核調(diào)試宏

          下面是Android touchscreen驅(qū)動(dòng)的調(diào)試宏用法,看這樣的寫法就是一個(gè)大神了,給大家借鑒。

          //?Log?define
          #define?GTP_ERROR(fmt,arg...)??????????printk("<<-GTP-ERROR->>?"fmt"\n",##arg)
          #if?DEBUG_SWITCH
          #define?GTP_INFO(fmt,arg...)???????????printk("<<-GTP-INFO->>?"fmt"\n",##arg)
          #define?GTP_DEBUG(fmt,arg...)??????????do{\
          ?????????????????????????????????????????if(GTP_DEBUG_ON)\
          ?????????????????????????????????????????printk("<<-GTP-DEBUG->>?[%d]"fmt"\n",__LINE__,?##arg);\
          ???????????????????????????????????????}while(0)
          #define?GTP_DEBUG_ARRAY(array,?num)????do{\
          ?????????????????????????????????????????s32?i;\
          ?????????????????????????????????????????u8*?a?=?array;\
          ?????????????????????????????????????????if(GTP_DEBUG_ARRAY_ON)\
          ?????????????????????????????????????????{\
          ????????????????????????????????????????????printk("<<-GTP-DEBUG-ARRAY->>\n");\
          ????????????????????????????????????????????for?(i?=?0;?i?????????????????????????????????????????????{\
          ????????????????????????????????????????????????printk("%02x???",?(a)[i]);\
          ????????????????????????????????????????????????if?((i?+?1?)?%10?==?0)\
          ????????????????????????????????????????????????{\
          ????????????????????????????????????????????????????printk("\n");\
          ????????????????????????????????????????????????}\
          ????????????????????????????????????????????}\
          ????????????????????????????????????????????printk("\n");\
          ????????????????????????????????????????}\
          ???????????????????????????????????????}while(0)
          #define?GTP_DEBUG_FUNC()???????????????do{\
          ?????????????????????????????????????????if(GTP_DEBUG_FUNC_ON)\
          ?????????????????????????????????????????printk("?????<<-GTP-FUNC->>???????Func:%s@Line:%d\n",__func__,__LINE__);\
          ???????????????????????????????????????}while(0)

          #else
          #define?GTP_INFO(fmt,arg...)
          #define?GTP_DEBUG(fmt,arg...)
          #define?GTP_DEBUG_ARRAY(array,?num)
          #define?GTP_DEBUG_FUNC()
          #endif


          推薦閱讀:


          嵌入式編程專輯
          Linux 學(xué)習(xí)專輯
          C/C++編程專輯
          Qt進(jìn)階學(xué)習(xí)專輯

          歡迎關(guān)注微信公眾號(hào)-嵌入式Linux

          瀏覽 41
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          評(píng)論
          圖片
          表情
          推薦
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          <kbd id="afajh"><form id="afajh"></form></kbd>
          <strong id="afajh"><dl id="afajh"></dl></strong>
            <del id="afajh"><form id="afajh"></form></del>
                1. <th id="afajh"><progress id="afajh"></progress></th>
                  <b id="afajh"><abbr id="afajh"></abbr></b>
                  <th id="afajh"><progress id="afajh"></progress></th>
                  一级片视频在线观看大全 | 四虎影院久久 | 亚洲精品少妇 | 频逼特逼在线视频 | 国产毛片AV一区二区三区牛牛影视 |