手動建立makefile簡單例項解析

2021-08-30 05:01:20 字數 4018 閱讀 7047

假設我們有乙個程式由5個檔案組成,源**如下:

/*main.c*/

#include "mytool1.h"

#include "mytool2.h"

int main()

/*mytool1.c*/

#include "mytool1.h"

#include

void mytool1_print(char *print_str)

/*mytool1.h*/

#ifndef _mytool_1_h

#define _mytool_1_h

void mytool1_print(char *print_str);

#endif

/*mytool2.c*/

#include "mytool2.h"

#include

void mytool2_print(char *print_str)

/*mytool2.h*/

#ifndef _mytool_2_h

#define _mytool_2_h

void mytool2_print(char *print_str);

#endif

首先了解一下make和makefile。gnu make是乙個工程管理器,它可以管理較多的檔案。我所使用的redhat 9.0的make版本為gnu make version 3.79.1。使用make的最大好處就是實現了「自動化編譯」。如果有乙個上百個檔案的**構成的專案,其中乙個或者幾個檔案進行了修改,make就能夠自動識別更新了的檔案**,不需要輸入冗長的命令列就可以完成最後的編譯工作。make執行時,自動尋找makefile(makefile)檔案,然後執行編譯工作。所以我們需要編寫makefile檔案,這樣可以提高實際專案的工作效率。

在乙個makefile中通常包含下面內容:

1、需要由make工具建立的目標體(target),通常是目標檔案或可執行檔案。

2、要建立的目標體所依賴的檔案(dependency_file)。

3、建立每個目標體時需要執行的命令(command)。

格式如下:

target:dependency_files

command

target:規則的目標。通常是程式中間或者最後需要生成的檔名,可以是.o檔案、也可以是最後的可執行程式的檔名。另外,目標也可以是乙個make執行的動作的名稱,如目標「clean」,這樣的目標稱為「偽目標」。

dependency_files:規則的依賴。生成規則目標所需要的檔名列表。通常乙個目標依賴於乙個或者多個檔案。

command:規則的命令列。是make程式所有執行的動作(任意的shell命令或者可在shell下執行的程式)。乙個規則可以有多個命令列,每一條命令佔一行。注意:每乙個命令列必須以[tab]字元開始,[tab]字元告訴make此行是乙個命令列。make按照命令完成相應的動作。這也是書寫makefile中容易產生,而且比較隱蔽的錯誤。命令就是在任何乙個目標的依賴檔案發生變化後重建目標的動作描述。乙個目標可以沒有依賴而只有動作(指定的命令)。比如makefile中的目標「clean」,此目標沒有依賴,只有命令。它所指定的命令用來刪除make過程產生的中間檔案(清理工作)。

在makefile中「規則」就是描述在什麼情況下、如何重建規則的目標檔案,通常規則中包括了目標的依賴關係(目標的依賴檔案)和重建目標的命令。make執行重建目標的命令,來建立或者重建規則的目標(此目標檔案也可以是觸發這個規則的上乙個規則中的依賴檔案)。規則包含了目標和依賴的關係以及更新目標所要求的命令。

makefile中可以包含除規則以外的部分。乙個最簡單的makefile可能只包含規則描述。規則在有些makefile中可能看起來非常複雜,但是無論規則的書寫是多麼的複雜,它都符合規則的基本格式。

下面就可以寫出第乙個makefile了。

main:main.o mytool1.o mytool2.o

gcc -o main main.o mytool1.o mytool2.o

main.o:main.c mytool1.h mytool2.h

gcc -c main.c

mytool1.o:mytool1.c mytool1.h

gcc -c mytool1.c

mytool2.o:mytool2.c mytool2.h

gcc -c mytool2.c

clean:

rm -f *.o main

在shell提示符下輸入make,執行顯示:

gcc -c main.c

gcc -c mytool1.c

gcc -c mytool2.c

gcc -o main main.o mytool1.o mytool2.o

執行結果如下:

[armlinux@lqm makefile-easy]$ ./main

this is mytool1 print : hello mytool1!

this is mytool2 print : hello mytool2!

這只是最為初級的makefile,現在來對這個makefile進行改進。

改進一:使用變數

一般在書寫makefile時,各部分變數引用的格式如下:

1. make變數(makefile中定義的或者是make的環境變數)的引用使用「$(var)」格式,無論「var」是單字元變數名還是多字元變數名。

2. 出現在規則命令列中shell變數(一般為執行命令過程中的臨時變數,它不屬於makefile變數,而是乙個shell變數)引用使用shell的「$tmp」格式。

3. 對出現在命令列中的make變數同樣使用「$(cmdvar)」 格式來引用。

obj=main.o mytool1.o mytool2.o

make:$(obj)

gcc -o main $(obj)

main.o:main.c mytool1.h mytool2.h

gcc -c main.c

mytool1.o:mytool1.c mytool1.h

gcc -c mytool1.c

mytool2.o:mytool2.c mytool2.h

gcc -c mytool2.c

clean:

rm -f main $(obj)

改進二:使用自動推導

讓make自動推導,只要make看到乙個.o檔案,它就會自動的把對應的.c檔案加到依賴檔案中,並且gcc -c .c也會被推導出來,所以makefile就簡化了。

cc = gcc

obj = main.o mytool1.o mytool2.o

make: $(obj)

$(cc) -o main $(obj)

main.o: mytool1.h mytool2.h

mytool1.o: mytool1.h

mytool2.o: mytool2.h

.phony: clean

clean:

rm -f main $(obj)

改進三:自動變數($^ $< $@)的應用

makefile 有三個非常有用的變數,分別是$@、$^、$<。代表的意義分別是:

$@--目標檔案,

$^--所有的依賴檔案,

$<--第乙個依賴檔案。

cc = gcc

obj = main.o mytool1.o mytool2.o

main: $(obj)

$(cc) -o $@ $^

main.o: main.c mytool1.h mytool2.h

$(cc) -c $<

mytool1.o: mytool1.c mytool1.h

$(cc) -c $<

mytool2.o: mytool2.c mytool2.h

$(cc) -c $<

.phony: clean

clean:

rm -f main $(obj)

這些是最為初級的知識,現在至少可以減少編譯時的工作量。細節方面的東西還需要在以後的工作和學習中不斷的總結,不斷的深化理解。可以 參考gnu make手冊,這裡講解的比較全面。

手動建立簡單CHM幫助檔案

chm是英語 compiled help manual 的簡寫,即 已編譯的幫助檔案 這是乙個html格式的幫助文件,原始檔就是html檔案以及jpg gif等等html所支援的元素。網上有許多的資料介紹如何建立chm幫助檔案,更多的只是推薦使用工具來建立,如微軟官方的mircosoft html ...

手動建立簡單webpack專案及React使用

1 執行 npm init y 快速初始化專案 2 在專案根目錄建立src的源 目錄和dist產品目錄 3 在src目錄下建立 index.html 4 使用cnpm 下安裝 webpack,執行cnpm i webpack webpack cli d 5 注意webpack 4.x 提供了 約定大...

手動建立DataTable

方法一 datatable tbldatas new datatable datas datacolumn dc null dc tbldatas.columns.add id type.gettype system.int32 dc.autoincrement true 自動增加 dc.autoi...