電子產(chǎn)業(yè)一站式賦能平臺

PCB聯(lián)盟網(wǎng)

搜索
查看: 92|回復(fù): 0
收起左側(cè)

不懂 Makefile 的程序員還敢寫代碼嗎?

[復(fù)制鏈接]

317

主題

317

帖子

3149

積分

四級會員

Rank: 4

積分
3149
跳轉(zhuǎn)到指定樓層
樓主
發(fā)表于 2024-12-6 10:34:00 | 只看該作者 回帖獎勵 |正序瀏覽 |閱讀模式
前言:編譯命令敲累了?是時候?qū)W點自動化了!每次編譯項目是不是手動敲gcc 命令? 當(dāng)項目文件一多,命令就像繞口令一樣——又長又復(fù)雜,還特別容易出錯。
別怕,今天我就帶你認(rèn)識一個“懶人神器”——Makefile。
用 Makefile 的好處很簡單:
  • 代碼編譯自動化,輕松又高效;
  • 不用手動敲命令,少掉坑;
  • 項目多大都不怕,它全能搞定。只要學(xué)會寫 Makefile,編譯這種枯燥的事情,再也不用你操心!讓我們從零開始,一步步帶你搞清楚它是啥、怎么寫,看完就能用!
    1、什么是 Makefile?Makefile 就是一個編譯指揮官,你把編譯規(guī)則寫在里面,之后用一條簡單的命令make,它就會按照規(guī)則自動完成所有的編譯任務(wù)。
    打個比方,你是項目經(jīng)理,Makefile 就是你的筆記本,記錄著項目的“施工計劃”:
  • 每個目標(biāo)(比如可執(zhí)行文件main)的來源(哪些源文件);
  • 這些目標(biāo)要用什么命令生成;
  • 有哪些需要重復(fù)利用的部分(比如中間文件*.o)。一句話:Makefile 幫你自動化處理那些又多又煩的編譯流程!
    2、為什么用 Makefile?假設(shè)你有兩個源文件:main.c 和utils.c,手動編譯步驟大概是這樣:
  • 先把main.c 和utils.c 分別編譯成目標(biāo)文件:[/ol]gcc -c main.c -o main.o
    gcc -c utils.c -o utils.o 2. 再把目標(biāo)文件鏈接成可執(zhí)行文件:gcc main.o utils.o -o main
    看著簡單,但代碼一多,命令就會變成這樣:
    gcc -c file1.c -o file1.o
    gcc -c file2.c -o file2.o
    gcc -c file3.c -o file3.o
    ...
    gcc file1.o file2.o file3.o -o my_program
    多打一條命令,多一個機會掉坑;一改代碼,又得全編譯一遍,時間都浪費了。
    用 Makefile,只需要:
    make
    一條命令,全搞定!而且它還會只編譯改動的文件,效率直接起飛。
    簡單理解:
  • 沒有 Makefile:自己手敲命令,累。
  • 有了 Makefile:只用一句make,剩下的事全自動完成,爽。3、Makefile 的基本結(jié)構(gòu) (一分鐘搞懂)Makefile 是由一組規(guī)則(rule)組成的,每個規(guī)則都包含三部分:
  • 目標(biāo)(target):你想要生成的文件,比如main。
  • 依賴(dependencies):目標(biāo)文件需要哪些源文件或頭文件。
  • 命令(commands):生成目標(biāo)需要運行的命令。[/ol]舉個例子:
    main: main.o utils.o
    gcc main.o utils.o -o main
      
    main.o: main.c
        gcc -c main.c
    utils.o: utils.c
        gcc -c utils.c
    什么意思呢?
    上面總共 3 條規(guī)則,來說說第一條規(guī)則:
  • 目標(biāo)是main,表示我們要生成一個叫main 的可執(zhí)行文件。
  • 依賴是main.o 和utils.o,也就是說生成main 需要這兩個依賴文件先生成,而這兩個依賴是利用規(guī)則 2 和 規(guī)則 3 生成的。
  • 命令是gcc main.o utils.o -o main,它負(fù)責(zé)把.o 文件編譯成最終的可執(zhí)行文件。[/ol]后兩條規(guī)則類似,告訴make 怎么生成main.o 和utils.o。
    簡單嗎?這就相當(dāng)于告訴 Makefile:“你要先準(zhǔn)備好main.o 和utils.o,然后用 gcc 鏈接它們!
    4、Makefile 基礎(chǔ)功能:讓編譯自動化從這里開始4.1 自動生成目標(biāo)文件如果你每次都向上面一樣手寫main.o、utils.o 的生成規(guī)則,那 Makefile 就會變得非常繁瑣和重復(fù)。好消息是,Makefile 支持通配符,可以自動生成規(guī)則!
    %.o: %.c
    gcc -c $ -o $@
    這段代碼怎么用?假設(shè)你有main.c 和utils.c,Makefile 會自動生成對應(yīng)的規(guī)則:
  • main.o:由main.c 生成,命令是gcc -c main.c -o main.o;
  • utils.o:由utils.c 生成,命令是gcc -c utils.c -o utils.o。解釋一下符號:
  • %.o 和%.c:% 是通配符,表示文件名匹配,比如main.o 和main.c。
  • $:依賴文件,比如main.c。
  • $@:目標(biāo)文件,比如main.o。用這個規(guī)則,Makefile 直接幫你生成所有目標(biāo)文件,舒服吧?
    而當(dāng)項目文件越多,使用 Makefile 的優(yōu)勢就越大。
    4.2 增量編譯:只編譯改動的文件Makefile 有個超棒的功能:只編譯需要更新的文件。
    它會檢查每個目標(biāo)的依賴文件,如果依賴文件沒有變化,就跳過編譯。
    比如你改了main.c,Makefile 只會重新生成main.o,而utils.o 完全不動。
    這個功能在項目文件很多的時候,能節(jié)省一大堆時間。
    4.3 清理臨時文件編譯后,會留下很多.o 文件和中間文件。Makefile 可以加一個clean 規(guī)則,幫你一鍵清理:
    clean:
    rm -f *.o main
    直接運行make clean,干凈清爽!
    5、Makefile 的進階玩法了解了基本用法后,咱們來看一些能提升開發(fā)效率的進階功能。
    5.1 基礎(chǔ)玩法 - 提高可讀性和可維護性1. 使用變量:讓 Makefile 更加簡潔變量怎么使用?比如CC = gcc。變量可以讓 Makefile 更加靈活和易維護。
    變量的基本用法:
    # 定義變量
    CC = gcc
    CFLAGS = -Wall -g
    TARGET = main
    SRCS = main.c utils.c
    OBJS = $(SRCS:.c=.o)
    # $(SRCS:.c=.o) 是 Makefile 中的一種變量替換,它的作用是把變量 SRCS 中的每個 .c 文件名換成對應(yīng)的 .o 文件名。
    # 替換之后 OBJS = main.o utils.o
    在命令中使用變量時,需要用$() 的形式引用:
    $(TARGET): $(OBJS)
    $(CC) $(CFLAGS) $(OBJS) -o $(TARGET)
       
    # 使用$()替換變量之后的規(guī)則如下:   
    main: main.o utils.o
    gcc -Wall -g main.o utils.o -o main
    這樣,如果你要修改編譯器或優(yōu)化選項,只需要改動變量部分,而不需要手動修改每條規(guī)則。
    2、偽目標(biāo):讓 Makefile 更靈活在 Makefile 中,有些目標(biāo)(比如clean)不會生成文件,而是用來執(zhí)行特定的命令,比如清理臨時文件。這種目標(biāo)我們稱為 偽目標(biāo)。
    問題來了:如果目錄中剛好有個文件名就叫clean,運行make clean 時,Makefile 會誤以為這個文件已經(jīng)存在,導(dǎo)致規(guī)則不執(zhí)行。
    怎么解決?
    用.PHONY 聲明偽目標(biāo),告訴make 這個目標(biāo)不是文件,應(yīng)該直接執(zhí)行命令。
    示例:聲明偽目標(biāo)
    .PHONY: clean
    clean:
    rm -f $(OBJS) $(TARGET)
    這樣,即使目錄中有個名為clean 的文件,make clean 仍然會按規(guī)則執(zhí)行,刪除目標(biāo)文件和中間文件。
    記。悍彩遣簧晌募哪繕(biāo),都建議用.PHONY 聲明!
    5.2  進階玩法 - 構(gòu)建更強大的 Makefile1、模式規(guī)則:適配更多文件類型有時候我們的項目里,不只有.c 文件,還有.cpp 文件。如果要分別寫規(guī)則,那就太麻煩了!這時候,模式規(guī)則 就能幫上大忙。
    什么是模式規(guī)則?
    模式規(guī)則就是一種通用規(guī)則,用來告訴 Makefile:
    “遇到這種類型的文件,該怎么處理!
    比如,告訴 Makefile:
  • .c 文件用gcc 編譯;
  • .cpp 文件用g++ 編譯。這樣,Makefile 會根據(jù)文件后綴自動選擇正確的規(guī)則,不用你手動一個一個寫。
    怎么用?支持 C++ 文件
    假設(shè)項目里有.cpp 文件,我們可以加一個模式規(guī)則:
    %.o: %.cpp
    g++ -c $ -o $@
    這樣,Makefile 會自動把所有.cpp 文件編譯成.o 文件,完全不用你操心。
    如何同時支持 C 和 C++ 文件?
    如果項目里既有.c 文件,也有.cpp 文件,那我們可以寫兩條規(guī)則:
    %.o: %.c
    $(CC) $(CFLAGS) -c $ -o $@
    %.o: %.cpp
    g++ -c $ -o $@
    這兩條規(guī)則的作用:
  • 第一條:告訴 Makefile,.c 文件用gcc 編譯。
  • 第二條:告訴 Makefile,.cpp 文件用g++ 編譯。[/ol]這樣,不管你的文件是.c 還是.cpp,Makefile 都會自動搞定。
    總結(jié)一下:
  • 它會根據(jù)文件類型,自動選擇合適的編譯方式;
  • 你只需要寫一條規(guī)則,Makefile 就能幫你搞定一大堆文件;
  • 再也不用重復(fù)寫規(guī)則了,省事又高效!記住:文件后綴不同?用模式規(guī)則全搞定!
    2、條件語句:讓 Makefile 更聰明條件語句可以讓 Makefile 根據(jù)實際情況調(diào)整規(guī)則,比如不同的操作系統(tǒng)、不同的編譯模式,用起來既靈活又省心。
    1、適配不同平臺
    不同操作系統(tǒng)的命令可能不一樣,比如刪除文件,Linux 用rm,Windows 用del。通過條件語句,Makefile 可以自動選擇正確的命令:
    OS = $(shell uname)
    ifeq ($(OS), Linux)
    CLEAN_CMD = rm -f
    else
    CLEAN_CMD = del
    endif
    clean:
    $(CLEAN_CMD) *.o $(TARGET)
  • 在 Linux 上運行make clean:執(zhí)行rm -f;
  • 在 Windows 上運行make clean:執(zhí)行del。這樣,無論在哪個平臺都不用手動改命令了,省事!
    2、切換編譯模式
    開發(fā)過程中經(jīng)常需要在調(diào)試模式(debug)和發(fā)布模式(release)之間切換:
  • 調(diào)試模式:包含調(diào)試信息(方便排查問題)。
  • 發(fā)布模式:優(yōu)化性能(適合生產(chǎn)環(huán)境)。用條件語句很容易實現(xiàn):
    ifeq ($(MODE), debug)
    CFLAGS = -g -O0
    else
    CFLAGS = -O2
    endif
    all:
    $(CC) $(CFLAGS) -o $(TARGET) $(SRCS)
  • 運行調(diào)試模式:make MODE=debug
    用-g 和-O0 編譯,生成帶調(diào)試信息的程序。
  • 運行發(fā)布模式:make
    或:
    make MODE=release
    用-O2 編譯,生成優(yōu)化后的高性能程序。
    小結(jié)一下
  • 適配不同平臺: 條件語句讓 Makefile 在 Linux 和 Windows 上都能用。
  • 切換編譯模式: 方便開發(fā)階段調(diào)試和生產(chǎn)環(huán)境優(yōu)化。3、自動化依賴管理: 讓 Makefile 更聰明!在寫代碼時,.c 文件往往會用到頭文件.h。比如,你的main.c 里可能有一句:
    #include "utils.h"
    如果有一天你修改了utils.h,Makefile 怎么知道它需要重新編譯main.c 呢?
    靠你手動寫依賴規(guī)則?別開玩笑了,項目文件一多,光靠手動寫依賴會把人累趴。
    這時候,自動化依賴管理就派上用場了。
    什么是自動化依賴管理?
  • 自動化依賴管理的核心是用gcc -M 命令,它能幫你自動生成.c 文件和.h 文件的依賴關(guān)系。每次你修改頭文件時,Makefile 會自動觸發(fā)相關(guān)的.c 文件重新編譯。代碼怎么寫?
    看下面這個 Makefile 示例:
    # 定義依賴文件列表
    DEPS = $(SRCS:.c=.d)
    # 生成 .d 文件,寫入依賴規(guī)則
    %.d: %.c
    $(CC) -M $ > $@
    # 包含依賴文件
    include $(DEPS)
    它到底做了什么?
  • 定義依賴文件[/ol]DEPS = $(SRCS:.c=.d)
    把源文件列表SRCS 中的每個.c 文件,替換成對應(yīng)的.d 文件,比如:
  • main.c →main.d
  • utils.c →utils.d這些.d 文件就是用來記錄.c 和.h 之間的關(guān)系。
    2. 自動生成依賴規(guī)則
    %.d: %.c
    $(CC) -M $ > $@
    這條規(guī)則會用gcc -M 為每個.c 文件生成一個.d 文件,里面記錄了它依賴哪些頭文件。
    比如,如果你的main.c 包含了utils.h,生成的main.d 文件可能是這樣的:
    main.o: main.c utils.h3. 包含依賴規(guī)則include $(DEPS)
    這句話告訴 Makefile,把所有.d 文件里的內(nèi)容加載進來。每次運行 Makefile 時,它都會檢查.d 文件里的規(guī)則,看哪些文件需要重新編譯。
    效果如何?
    假設(shè)你有以下文件:
  • main.c 依賴utils.h;
  • utils.c 不依賴任何頭文件。如果你修改了utils.h,Makefile 會自動發(fā)現(xiàn)這個改動,然后只重新編譯main.c,而不會動utils.c。
    自動化依賴管理的好處:
  • 再也不用手動寫依賴規(guī)則,讓 Makefile 更智能;
  • 每次頭文件更新時,Makefile 自動判斷哪些文件需要重新編譯;
  • 即使項目文件多到爆,也能輕松應(yīng)對。[/ol]簡單記。骸坝.h 文件,就用gcc -M 自動生成依賴!”
    4、多目標(biāo)支持:用 Makefile 管理多個模塊當(dāng)你的項目文件越來越多,甚至分成了多個模塊,比如lib 是核心功能模塊,app 是主程序模塊,光靠一個 Makefile 已經(jīng)很難搞定了。
    這時候,聰明的做法是:
  • 每個模塊有自己的 Makefile,單獨管理自己的規(guī)則;
  • 用一個主 Makefile 調(diào)度所有模塊,讓項目更清晰、更高效!分模塊的做法:
    1. 給每個模塊單獨寫一個 Makefile
    比如,在lib 模塊的目錄下,我們寫一個lib/Makefile:
    # lib/Makefile
    lib.a: lib.o               # 定義目標(biāo) lib.a
    ar rcs lib.a lib.o       # 把 lib.o 打包成靜態(tài)庫 lib.a
    lib.o: lib.c               # 編譯規(guī)則:生成 lib.o
    gcc -c lib.c -o lib.o
  • lib.a 是靜態(tài)庫,ar rcs 是打包命令。
  • 這個 Makefile 只關(guān)心lib 模塊自己的文件,不影響其他模塊。2. 用主 Makefile 調(diào)度所有模塊
    主 Makefile 位于項目根目錄,負(fù)責(zé)把所有模塊串起來。它并不關(guān)心每個模塊的具體規(guī)則,而是遞歸調(diào)用每個模塊自己的 Makefile:
    # 主 Makefile
    SUBDIRS = lib app          # 定義模塊目錄
    all: $(SUBDIRS)            # 主目標(biāo):編譯所有模塊
    $(SUBDIRS):                # 遞歸調(diào)用每個模塊的 Makefile
    $(MAKE) -C $@
    clean:                     # 清理所有模塊
    for dir in $(SUBDIRS); do $(MAKE) -C $$dir clean; done
    代碼解釋:
    1. SUBDIR 是模塊列表:這里定義了項目中的模塊,比如lib 和app。每個模塊目錄都有自己的 Makefile。
    2. $(MAKE) -C $@  是關(guān)鍵:這條命令的意思是切換到指定目錄(-C),然后運行這個目錄里的 Makefile。比如,$(MAKE) -C lib 就是到lib 目錄運行它的 Makefile。
    [/ol]3. 遞歸清理 :  clean 目標(biāo)會循環(huán)進入每個模塊目錄,調(diào)用它們的clean 規(guī)則。注意$$dir 中的雙$,是為了讓 Makefile 能正確解析。
    整體效果:
  • 你可以在主目錄運行make,它會自動編譯所有模塊;
  • 運行make clean 時,它會遞歸清理所有模塊的臨時文件;
  • 每個模塊的規(guī)則獨立,清晰又方便維護。用主 Makefile 調(diào)度多個模塊的好處:
  • 結(jié)構(gòu)清晰:每個模塊的規(guī)則獨立管理,主 Makefile 只負(fù)責(zé)調(diào)度。
  • 易于維護:修改或新增模塊時,只需在SUBDIRS 添加對應(yīng)模塊目錄即可。
  • 高效遞歸:通過$(MAKE) -C 調(diào)用子目錄的 Makefile,模塊間互不干擾。[/ol]簡單來說:分模塊管理,用主 Makefile 調(diào)度,一切井井有條!
    5.3 高階玩法 - 優(yōu)化效率與靈活性1. 并行編譯:提高效率Makefile 的make 命令支持并行執(zhí)行多個規(guī)則,用-j 參數(shù)指定并行任務(wù)數(shù)。
    示例:并行編譯
    make -j4
    這會同時運行最多 4 個任務(wù),充分利用多核 CPU,顯著提升大項目的編譯速度。
    2. 自定義函數(shù):復(fù)用邏輯在寫 Makefile 時,如果規(guī)則中有重復(fù)的編譯邏輯,比如把.c 文件編譯成.o 文件,一直重復(fù)寫$(CC) $(CFLAGS) 就很麻煩。這時候,我們可以用自定義函數(shù)來統(tǒng)一管理這些重復(fù)操作,既方便又省事!
    定義函數(shù):
    用define 和endef 定義一個編譯函數(shù):
    define compile
    $(CC) $(CFLAGS) -c $ -o $@
    endef
  • compile 是函數(shù)名,表示編譯的邏輯;
  • $ 是依賴文件(比如main.c),$@ 是目標(biāo)文件(比如main.o)。使用函數(shù):
    調(diào)用自定義函數(shù)時,用$(call 函數(shù)名):
    %.o: %.c
    $(call compile)
    這條規(guī)則會自動把.c 文件編譯成對應(yīng)的.o 文件。
    小結(jié)一下:
  • 自定義函數(shù)減少了重復(fù)代碼;
  • 修改邏輯時,只需改函數(shù)定義,其他地方不用動;
  • 讓 Makefile 簡潔易讀,清晰高效。[/ol]一句話:把重復(fù)的邏輯封裝成函數(shù),Makefile 也能優(yōu)雅起來!
    3. 靜態(tài)模式規(guī)則:批量生成目標(biāo)文件當(dāng)多個文件需要用相似的規(guī)則編譯時,一個個寫太麻煩,用靜態(tài)模式規(guī)則 就能一次性搞定!
    先來看個簡單示例: 假設(shè)我們要把多個.c 文件編譯成.o 文件:
    OBJS = main.o utils.o io.o
    $(OBJS): %.o: %.c
    $(CC) $(CFLAGS) -c $ -o $@
    這是什么意思?
  • $(OBJS) 是目標(biāo)文件列表,比如main.o、utils.o;
  • %.o: %.c 說明每個.o 文件由對應(yīng)的.c 文件生成;
  • $ 是源文件(如main.c),$@ 是目標(biāo)文件(如main.o)。優(yōu)點:
  • 減少重復(fù):一條規(guī)則批量處理,省時省力;
  • 自動匹配:文件名自動對應(yīng),無需手動寫每條規(guī)則。[/ol]這里順便提下 通配模式規(guī)則,這兩種模式用法很相似。
    對于更簡單的項目,你可以用通配模式規(guī)則來實現(xiàn)類似效果:
    %.o: %.c
    $(CC) $(CFLAGS) -c $ -o $@
    解釋一下:
  • 每個.o 文件由對應(yīng)的.c 文件生成;
  • 通配符% 會匹配任意文件名,比如main.c 自動對應(yīng)main.o。靜態(tài)模式規(guī)則 vs. 通配模式規(guī)則
    特性靜態(tài)模式規(guī)則通配模式規(guī)則匹配范圍針對特定目標(biāo)列表(如$(OBJS)
    )自動匹配所有符合%
    的文件靈活性控制更精確,只處理指定的目標(biāo)文件簡單統(tǒng)一,適合全局規(guī)則適用場景文件多、規(guī)則復(fù)雜,特定文件需要特殊處理文件少、規(guī)則統(tǒng)一,簡單項目總結(jié):
  • 通配模式規(guī)則適合簡單項目,一條規(guī)則處理所有文件;
  • 靜態(tài)模式規(guī)則適合復(fù)雜項目,可以精確控制哪些文件應(yīng)用規(guī)則。記。汉唵稳钟猛ㄅ,精準(zhǔn)處理選靜態(tài)!
    4. 跨平臺構(gòu)建:用 CMake 生成 Makefile如果項目需要在多個平臺(如 Windows、Linux、macOS)上編譯,直接寫 Makefile 會很麻煩。這時,可以用 CMake 自動生成適配不同平臺的 Makefile。
    使用方法:
    1. 創(chuàng)建 CMake 配置文件
    在項目目錄下新建CMakeLists.txt,內(nèi)容如下:
  • # 聲明最低版本要求cmake_minimum_required(VERSION 3.10)
    # 定義項目名稱project(MyProject)
    # 指定可執(zhí)行文件add_executable(main main.c utils.c)2. 生成 Makefile
    在終端運行:
    cmake .
    3. 編譯項目
    使用生成的 Makefile:
    make
    優(yōu)點:
  • 跨平臺:適配 Windows、Linux、macOS 等操作系統(tǒng);
  • 簡化管理:無需手寫復(fù)雜的 Makefile。一句話總結(jié):用 CMake 自動生成 Makefile,跨平臺編譯就是這么簡單!
    五、完整示例結(jié)合前面學(xué)到的內(nèi)容,來看看一個完整的 Makefile:
    # 定義變量
    CC = gcc                     # 編譯器
    CFLAGS = -Wall -g            # 編譯參數(shù):開啟所有警告和調(diào)試信息
    SRCS =  $(wildcard *.c)      # 獲取當(dāng)前目錄下所有的 .c 文件,并賦值給 SRCS 變量,例如:SRCS = main.c utils.c
    OBJS = $(SRCS:.c=.o)         # 把 .c 文件替換成 .o 文件,替換之后,OBJS = main.o utils.o
    TARGET = main                # 最終生成的可執(zhí)行文件
    # 編譯規(guī)則
    $(TARGET): $(OBJS)
    $(CC) $(CFLAGS) $(OBJS) -o $(TARGET)
    # 生成 .o 文件規(guī)則
    %.o: %.c
    $(CC) $(CFLAGS) -c $ -o $@
    # 加上 .PHONY 聲明偽目標(biāo)
    .PHONY: clean
    clean:
    rm -f $(OBJS) $(TARGET)
    使用:
  • make:生成 可執(zhí)行文件main;
  • make clean:會刪除所有.o 文件和可執(zhí)行文件main,保持項目目錄干凈。看了這篇文章,相信你看上面的 Makefile 代碼 應(yīng)該很輕松!六、寫在最后:從 Makefile 開始,走向編譯自動化!Makefile 就是編譯中的“懶人神器”,一旦用上,你會發(fā)現(xiàn):
  • 不再手動敲命令,編譯變得更簡單;
  • 即使項目越來越大,管理起來也毫不費力;
  • 提高效率,節(jié)省時間,輕松搞定復(fù)雜編譯!如果你還在手動敲命令,趕緊試試寫個 Makefile,體驗一下自動化的快樂吧~
    下篇文章我們將帶你進入 CMake 的世界,了解如何跨平臺管理項目,敬請期待!
    end

    一口Linux

    關(guān)注,回復(fù)【1024】海量Linux資料贈送
    精彩文章合集
    文章推薦
    ?【專輯】ARM?【專輯】粉絲問答?【專輯】所有原創(chuàng)?【專輯】linux入門?【專輯】計算機網(wǎng)絡(luò)?【專輯】Linux驅(qū)動?【干貨】嵌入式驅(qū)動工程師學(xué)習(xí)路線?【干貨】Linux嵌入式所有知識點-思維導(dǎo)圖
  • 回復(fù)

    使用道具 舉報

    發(fā)表回復(fù)

    您需要登錄后才可以回帖 登錄 | 立即注冊

    本版積分規(guī)則


    聯(lián)系客服 關(guān)注微信 下載APP 返回頂部 返回列表