青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品

興海北路

---男兒仗劍自橫行
<2008年4月>
303112345
6789101112
13141516171819
20212223242526
27282930123
45678910

統(tǒng)計

  • 隨筆 - 85
  • 文章 - 0
  • 評論 - 17
  • 引用 - 0

常用鏈接

留言簿(6)

隨筆分類

隨筆檔案

收藏夾

全是知識啊

搜索

  •  

最新評論

閱讀排行榜

評論排行榜

GCC編譯背后(第一部分:預(yù)處理和編譯)
by falcon <zhangjinw@gmail.com>

平時在Linux下寫代碼,直接用"gcc -o out in.c"就把代碼編譯好了,但是這后面到底做了什么事情呢?如果學習過編譯原理則不難理解,一般高級語言程序編譯的過程莫過于:預(yù)處理、編譯、匯編、鏈 接。gcc在后臺實際上也經(jīng)歷了這幾個過程,我們可以通過-v參數(shù)查看它的編譯細節(jié),如果想看某個具體的編譯過程,則可以分別使用-E,-S,-c和- O,對應(yīng)的后臺工具則分別為cpp,cc1,as,ld。下面我們將逐步分析這幾個過程以及相關(guān)的內(nèi)容,諸如語法檢查、代碼調(diào)試、匯編語言等。

1、預(yù)處理

    開篇簡述:預(yù)處理是C語言程序從源代碼變成可執(zhí)行程序的第一步,主要是C語言編譯器對各種預(yù)處理命令進行處理,包括頭文件的包含、宏定義的擴展、條件編譯的選擇等。

    以前沒怎么“深入”預(yù)處理,腦子對這些東西總是很模糊,只記得在編譯的基本過程(詞法分析、語法分析)之前還需要對源代碼中的宏定義、文件包含、條件編譯 等命令進行處理。這三類的指令很常見,主要有#define, #include和#ifdef ... #endif,要特別地注意它們的用法。(更多預(yù)處理的指令請查閱相關(guān)資料)

    #define除了可以獨立使用以便靈活設(shè)置一些參數(shù)外,還常常和#ifdef ... #endif結(jié)合使用,以便靈活地控制代碼塊的編譯與否,也可以用來避免同一個頭文件的多次包含。關(guān)于#include貌似比較簡單,通過man找到某個 函數(shù)的頭文件,copy進去,加上<>就okay。這里雖然只關(guān)心一些技巧,不過預(yù)處理還是蘊含著很多潛在的陷阱(可參考<C Traps & Pitfalls>),我們也需要注意的。下面僅介紹和預(yù)處理相關(guān)的幾個簡單內(nèi)容。

  • 打印出預(yù)處理之后的結(jié)果:gcc -E hello.c

        這樣我們就可以看到源代碼中的各種預(yù)處理命令是如何被解釋的,從而方便理解和查錯。

        實際上gcc在這里是調(diào)用了cpp的(雖然我們通過gcc的-v僅看到cc1),cpp即The C Preprocessor,主要用來預(yù)處理宏定義、文件包含、條件編譯等。下面介紹它的一個比較重要的選項-D。

  • 在命令行定義宏:gcc -Dmacro hello.c

        這個等同于在文件的開頭定義宏,即#define maco,但是在命令行定義更靈活。例如,在源代碼中有這些語句。
    #ifdef DEBUG
    printf("this code is for debugging\n");
    #endif

        如果編譯時加上-DDEBUG選項,那么編譯器就會把printf所在的行編譯進目標代碼,從而方便地跟蹤該位置的某些程序狀態(tài)。這樣-DDEBUG就可以當作一個調(diào)試開關(guān),編譯時加上它就可以用來打印調(diào)試信息,發(fā)布時則可以通過去掉該編譯選項把調(diào)試信息去掉。

    本節(jié)參考資料:
    [1] C語言教程第九章:預(yù)處理
    http://www.bc-cn.net/Article/kfyy/cyy/jc/200409/9.html
    [2] 更多
    http://www.hemee.com/kfyy/c/6626.html
    http://www.91linux.com/html/article/program/cpp/20071203/8745.html
    http://www.janker.org/bbs/programmer/2006-10-13/327.html

    2、編譯(翻譯)

        開篇簡要:編譯之前,C語言編譯器會進行詞法分析、語法分析(-fsyntax-only),接著會把源代碼翻譯成中間語言,即匯編語言。如果想看到這個 中間結(jié)果,可以用-S選項。需要提到的是,諸如shell等解釋語言也會經(jīng)歷一個詞法分析和語法分析的階段,不過之后并不會進行“翻譯”,而是“解釋”, 邊解釋邊執(zhí)行。

        把源代碼翻譯成匯編語言,實際上是編譯的整個過程中的第一個階段,之后的階段和匯編語言的開發(fā)過程沒有什么區(qū)別。這個階段涉及到對源代碼的詞法分析、語法檢查(通過-std指定遵循哪個標準),并根據(jù)優(yōu)化(-O)要求進行翻譯成匯編語言的動作。

        如果僅僅希望進行語法檢查,可以用-fsyntax-only選項;而為了使代碼有比較好的移植性,避免使用gcc的一些特性,可以結(jié)合-std和- pedantic(或者-pedantic-erros)選項讓源代碼遵循某個C語言標準的語法。這里演示一個簡單的例子。

    Quote:

    $ cat hello.c
    #include <stdio.h>
    int main()
    {
            printf("hello, world\n")
            return 0;
    }
    $ gcc -fsyntax-only hello.c
    hello.c: In function ‘main’:
    hello.c:5: error: expected ‘;’ before ‘return’
    $ vim hello.c
    $ cat hello.c
    #include <stdio.h>
    int main()
    {
            printf("hello, world\n");
            int i;
            return 0;
    }
    $ gcc -std=c89 -pedantic-errors hello.c    #默認情況下,gcc是允許在程序中間聲明變量的,但是turboc就不支持
    hello.c: In function ‘main’:
    hello.c:5: error: ISO C90 forbids mixed declarations and code



        語法錯誤是程序開發(fā)過程中難以避免的錯誤(人的大腦在很多條件下都容易開小差),不過編譯器往往能夠通過語法檢查快速發(fā)現(xiàn)這些錯誤,并準確地告訴你語法錯 誤的大概位置。因此,作為開發(fā)人員,要做的事情不是“恐慌”(不知所措),而是認真閱讀編譯器的提示,根據(jù)平時積累的經(jīng)驗(最好在大腦中存一份常見語法錯 誤索引,很多資料都提供了常見語法錯誤列表,如<C Traps&Pitfalls>和最后面的參考資料[12]也列出了很多常見問題)和編輯器提供的語法檢查功能(語法加亮、括號匹配提示 等)快速定位語法出錯的位置并進行修改。

        語法檢查之后就是翻譯動作,gcc提供了一個優(yōu)化選項-O,以便根據(jù)不同的運行平臺和用戶要求產(chǎn)生經(jīng)過優(yōu)化的匯編代碼。例如,

    Quote:

    $ gcc -o hello hello.c            #采用默認選項,不優(yōu)化
    $ gcc -O2 -o hello2 hello.c        #優(yōu)化等次是2
    $ gcc -Os -o hellos hello.c        #優(yōu)化目標代碼的大小
    $ ls -S hello hello2 hellos        #可以看到,hellos比較小,hello2比較大
    hello2  hello  hellos
    $ time ./hello
    hello, world

    real    0m0.001s
    user    0m0.000s
    sys     0m0.000s
    $ time ./hello2                #可能是代碼比較少的緣故,執(zhí)行效率看上去不是很明顯
    hello, world

    real    0m0.001s
    user    0m0.000s
    sys     0m0.000s

    $ time ./hellos                #雖然目標代碼小了,但是執(zhí)行效率慢了些
    hello, world

    real    0m0.002s
    user    0m0.000s
    sys     0m0.000s



        根據(jù)上面的簡單演示,可以看出gcc有很多不同的優(yōu)化選項,主要看用戶的需求了,目標代碼的大小和效率之間貌似存在一個“糾纏”,需要開發(fā)人員自己權(quán)衡。

        下面我們通過-S選項來看看編譯出來的中間結(jié)果,匯編語言,還是以之前那個hello.c為例。
    Quote:

    $ gcc -S hello.c        #默認輸出是hello.s,可自己指定,輸出到屏幕-o -,輸出到其他文件-o file
    $ cat hello.s
    cat hello.s
            .file   "hello.c"
            .section        .rodata
    .LC0:
            .string "hello, world"
            .text
    .globl main
            .type   main, @function
    main:
            leal    4(%esp), %ecx
            andl    $-16, %esp
            pushl   -4(%ecx)
            pushl   %ebp
            movl    %esp, %ebp
            pushl   %ecx
            subl    $4, %esp
            movl    $.LC0, (%esp)
            call    puts
            movl    $0, %eax
            addl    $4, %esp
            popl    %ecx
            popl    %ebp
            leal    -4(%ecx), %esp
            ret
            .size   main, .-main
            .ident  "GCC: (GNU) 4.1.3 20070929 (prerelease) (Ubuntu 4.1.2-16ubuntu2)"
            .section        .note.GNU-stack,"",@progbits



        不知道看出來沒?和我們在課堂里學的intel的匯編語法不太一樣,這里用的是AT&T語法格式。如果之前沒接觸過AT&T的,可以看看 參考資料[2]。如果想學習Linux下的匯編語言開發(fā),從下一節(jié)開始哦,下一節(jié)開始的所有章節(jié)基本上覆蓋了Linux下匯編語言開發(fā)的一般過程,不過這 里不介紹匯編語言語法。

        這里需要補充的是,在寫C語言代碼時,如果能夠?qū)幾g器比較熟悉(工作原理和一些細節(jié))的話,可能會很有幫助。包括這里的優(yōu)化選項(有些優(yōu)化選項可能在匯 編時采用)和可能的優(yōu)化措施,例如字節(jié)對齊(可以看看這本書"Linux_Assembly_Language_Programming"的第六小節(jié))、 條件分支語句裁減(刪除一些明顯分支)等。

    本節(jié)參考資料

    [1] Guide to Assembly Language Programming in Linux(pdf教程,社區(qū)有下載)
    http://oss.lzu.edu.cn/modules/wfdownloads/singlefile.php?cid=5&lid=94
    [2] Linux匯編語言開發(fā)指南(在線):
    http://www.ibm.com/developerworks/cn/linux/l-assembly/index.html
    [3] PowerPC 匯編
    http://www.ibm.com/developerworks/cn/linux/hardware/ppc/assembly/index.html
    [4] 用于 Power 體系結(jié)構(gòu)的匯編語言
    http://www.ibm.com/developerworks/cn/linux/l-powasm1.html
    [5] Linux Assembly HOWTO
    http://mirror.lzu.edu.cn/tldp/HOWTO/Assembly-HOWTO/
    [6] Linux 中 x86 的內(nèi)聯(lián)匯編
    http://www.ibm.com/developerworks/cn/linux/sdk/assemble/inline/index.html
    [7] Linux Assembly Language Programming
    http://mirror.lzu.edu.cn/doc/incoming/ebooks/linux-unix/Linux_EN_Original_Books

  • posted on 2008-03-14 15:22 隨意門 閱讀(918) 評論(0)  編輯 收藏 引用


    只有注冊用戶登錄后才能發(fā)表評論。
    網(wǎng)站導(dǎo)航: 博客園   IT新聞   BlogJava   博問   Chat2DB   管理


    青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品
  • <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>
            欧美freesex交免费视频| 免费高清在线视频一区·| 日韩视频在线永久播放| 香蕉免费一区二区三区在线观看 | 亚洲国产小视频| 久久电影一区| 一区二区三区不卡视频在线观看| 久久久久91| 国内精品久久久久影院优| 一本色道久久99精品综合| 欧美成人精品不卡视频在线观看| 亚洲一区二区三区四区中文| 欧美日韩情趣电影| 在线亚洲精品福利网址导航| 亚洲精选91| 欧美日韩免费一区| 亚洲一级电影| 9色porny自拍视频一区二区| 欧美日韩国产小视频| 亚洲免费观看高清在线观看 | 一区二区三区免费在线观看| 老鸭窝毛片一区二区三区| 久久久999国产| 激情文学综合丁香| 欧美一区二区三区婷婷月色 | 亚洲欧美成人综合| 在线中文字幕日韩| 国产精品久久久久久超碰| 亚洲欧美视频在线观看| 亚洲午夜精品网| 国产噜噜噜噜噜久久久久久久久| 亚洲欧美视频一区二区三区| 亚洲欧美日韩中文在线制服| 国产精品午夜久久| 欧美亚洲免费电影| 久久婷婷国产综合国色天香| 日韩亚洲不卡在线| 欧美日韩视频专区在线播放 | 欧美日韩一区二区视频在线| 免播放器亚洲| 国产亚洲精品成人av久久ww| 一本色道久久综合精品竹菊| 久久另类ts人妖一区二区| av不卡免费看| 另类尿喷潮videofree| 国产精品hd| 一区二区三区国产盗摄| 久久久久综合网| 亚洲欧美视频| 欧美日韩国产色视频| 一区二区三区亚洲| 久久黄色网页| 亚洲免费视频观看| 国产精一区二区三区| 亚洲视频国产视频| 亚洲欧洲一区二区三区| 久久婷婷成人综合色| 国产一区二区精品在线观看| 在线亚洲免费| 亚洲精品网站在线播放gif| 美女精品在线观看| 狠狠色综合网| 欧美一级专区| 亚洲午夜av| 国产精品电影网站| 亚洲午夜影视影院在线观看| 亚洲精品在线一区二区| 欧美黑人国产人伦爽爽爽| 最近看过的日韩成人| 欧美黄色片免费观看| 欧美成人免费网| 亚洲精品久久久一区二区三区| 久久婷婷国产综合精品青草| 欧美一区在线看| 国产一区二区三区在线免费观看| 欧美一区二区视频在线观看| 香蕉久久一区二区不卡无毒影院| 国产一区二区三区精品欧美日韩一区二区三区 | 亚洲欧洲日韩女同| 亚洲精品一区二区三区99| 欧美激情一区二区三区在线| 在线一区亚洲| 亚洲免费小视频| 国产一区二区三区四区五区美女 | 国产一区二区三区奇米久涩| 久久精品人人做人人爽电影蜜月| 香蕉成人伊视频在线观看| 国产一区二区三区电影在线观看| 久久精品在线| 欧美v日韩v国产v| 亚洲麻豆av| 一区二区三区四区五区精品| 国产日韩三区| 免费成人黄色片| 欧美日韩国产色综合一二三四 | 美女成人午夜| 欧美精品在线一区二区| 性做久久久久久久久| 久久国产手机看片| 亚洲视频在线观看视频| 欧美一区免费视频| 在线综合亚洲欧美在线视频| 午夜精品福利一区二区蜜股av| 精品av久久久久电影| 亚洲欧洲一区二区在线观看| 国产精品自拍小视频| 亚洲二区在线| 国产精品美女主播| 免费不卡中文字幕视频| 国产精品每日更新| 欧美黄色一级视频| 欧美三区在线| 美女图片一区二区| 国产精品影院在线观看| 最新高清无码专区| 国产亚洲欧洲| 亚洲午夜一二三区视频| 亚洲精品在线看| 久久精品国产免费| 欧美一二三视频| 欧美日韩国产在线播放| 麻豆精品视频在线| 国产日韩欧美一区二区三区在线观看| 最新日韩欧美| 亚洲激情一区二区| 久久精品欧美日韩精品| 欧美在线一二三四区| 欧美亚一区二区| 亚洲精品乱码视频| 亚洲精品韩国| 欧美成人亚洲成人| 久久久xxx| 国产真实乱偷精品视频免| 亚洲欧美综合国产精品一区| 亚洲一区图片| 欧美国产日韩免费| 亚洲区免费影片| 99日韩精品| 欧美日韩一区二区视频在线观看| 亚洲国产一成人久久精品| 亚洲国产精品成人| 久久九九热re6这里有精品 | 欧美一区二区三区四区在线 | 美女999久久久精品视频| 国产亚洲一级高清| 亚洲一区二区三区中文字幕| 亚洲欧美激情在线视频| 欧美日韩一区二区高清| 一区二区激情| 亚洲午夜久久久| 国产精品在线看| 欧美自拍偷拍| 欧美肥婆bbw| 亚洲美女一区| 欧美午夜无遮挡| 亚洲欧美日韩国产中文在线| 久久久久久一区二区三区| 国内精品视频在线播放| 久久久欧美精品sm网站| 欧美高清不卡| 亚洲一区二区三区精品在线| 国产精品一区二区在线观看不卡 | 欧美在线观看网站| 免费观看久久久4p| 亚洲精品乱码久久久久久黑人 | 亚洲高清视频的网址| 一区二区欧美日韩视频| 国产精品亚洲第一区在线暖暖韩国| 亚洲在线免费视频| 免费日韩精品中文字幕视频在线| 亚洲经典在线| 欧美日韩另类综合| 久久高清福利视频| 亚洲精品在线免费观看视频| 欧美一区二区在线观看| 亚洲电影免费在线观看| 欧美日韩国产一中文字不卡 | 欧美激情一区二区三区| 这里只有精品视频| 国内外成人在线视频| 欧美经典一区二区三区| 亚洲欧美日韩视频一区| 欧美成人一区二区三区| 亚洲视频欧美视频| 伊人久久久大香线蕉综合直播| 欧美精品久久久久久久免费观看| 亚洲制服欧美中文字幕中文字幕| 欧美国产精品| 久久午夜国产精品| 午夜免费电影一区在线观看| 亚洲日本成人| 国产精品一级| 欧美日韩一区二区视频在线观看 | 久久夜精品va视频免费观看| 正在播放欧美一区| 在线观看成人一级片| 欧美精品18+| 麻豆精品视频在线观看| 欧美一区精品| 午夜亚洲精品|