【Linux系統編程學習】 Makefile簡單入門

此為牛客網Linux C++課程1.10&1.11&1.12 的課程筆記。

0. Makefile介紹

在這里插入圖片描述

1. Makefile文件命名與規則

在這里插入圖片描述
在這里插入圖片描述
示例:
使用vim編寫如下名為Makefile的文件:

app:sub.o add.o mult.o div.o main.ogcc sub.o add.o mult.o div.o main.o -o appsub.o:sub.cgcc -c sub.c -o sub.oadd.o:add.cgcc -c add.c -o add.omult.o:mult.cgcc -c mult.c -o mult.odiv.o:div.cgcc -c div.c -o div.omain.o:main.cgcc -c main.c -o main.o

首先看第一行,app是我們的目標文件,冒號后面是生成該目標文件所需要的依賴,第二行是我們要執行的命令。
在使用sub.o add.o mult.o div.o main.o依賴時,發現目錄中沒有對應的.o文件,則向下尋找其他規則,執行以生成其依賴。注意,如果下面的規則中與第一行所需的依賴無關,則不會被執行,也就是說Makefile中的其他規則都是為第一條規則服務的。

2. 變量

在這里插入圖片描述
有了變量我們寫makefile就方便一些,比如我們之前的makefile就可以如此改寫:

src = sub.o add.o mult.o div.o main.o
target = app$(target):$(src)$(CC) $^ -o $(target)sub.o:sub.cgcc -c sub.c -o sub.oadd.o:add.cgcc -c add.c -o add.omult.o:mult.cgcc -c mult.c -o mult.odiv.o:div.cgcc -c div.c -o div.omain.o:main.cgcc -c main.c -o main.o

把所有的依賴定義為src變量,把目標文件名定義為target變量,然后用 $ 取值,其中 $ (CC)是預定義變量,表示C編譯器名稱;$^ 也是預定義變量,表示所有的依賴文件。

3. 模式匹配

在這里插入圖片描述
原先是按左邊的方式寫的,一個個寫很麻煩,這里可以使用模式匹配,即通配符%,在同一規則中,%匹配同一個字符串。
如此以來,之前的makefile可如此改寫:

src = sub.o add.o mult.o div.o main.o
target = app$(target):$(src)$(CC) $^ -o $(target)%.o:%.c$(CC) -c $< -o $@

src中的每一個依賴都可以匹配下面的這條規則。

4. 函數

現在通過模式匹配,避免了我們反復寫規則,但是依賴文件我們還是要一個一個寫在src里,有沒有辦法直接獲取這些文件的文件名呢?可以使用$(wildcard PATTERN…)函數。
在這里插入圖片描述
舉例,當前目錄如下:
在這里插入圖片描述

假如我們想讓在makefile文件中獲得當前目錄中所有.c文件的名稱,即可執行:

src = $ (wildcard ./*.c )

這樣就能獲得當前目錄下所有.c文件的名稱。
但是之前的示例代碼中需要的是與.c文件同名的.o文件,而目錄中沒有.o文件,我們可以使用$(patsubst < pattern>,< replacement>,< text>)函數:
在這里插入圖片描述
我們現在想要在makefile中獲得與目錄中.c文件同名的.o文件,便調用patsubst函數把獲得的.c文件進行字符串替換即可.
該函數的作用簡而言之就是把< text >中的匹配< pattern >的串用< replacement >代替。
其中< text >字段由剛才調用的src = $ (wildcard ./*.c )獲得,然后我們想將其中所有的.c都替換成.o,可將原來的makefile文件修改如下:

src = $(wildcard ./*.c)
objs = $(patsubst %.c, %.o, $(src))
target = app$(target):$(objs)$(CC) $^ -o $(target)%.o:%.c$(CC) -c $< -o $@

可實現與最初的示例程序相同的功能。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/384568.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/384568.shtml
英文地址,請注明出處:http://en.pswp.cn/news/384568.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

【Linux系統編程學習】 GDB調試器的簡單使用

此為牛客網Linux C課程 1.13&1.14&1.15&1.16 的課程筆記。 0. GDB簡介 1. 準備工作 想要使用gdb調試&#xff0c;首先需要用gcc的-g參數生成可執行文件&#xff0c;這樣才能在可執行文件中加入源代碼信息以便調試&#xff0c;但是注意這并不是將源文件嵌入到可執行…

【Linux系統編程學習】C庫IO函數與系統IO函數的關系

此為黑馬Linux課程筆記。 1. C標準IO函數工作流程 如圖&#xff0c;以C庫函數的fopen為例&#xff0c;其返回類型是FILE類型的指針&#xff0c;FILE類型包含很多內容&#xff0c;主要包含三個內容&#xff1a;文件描述符、文件讀寫指針的位置和I/O緩沖區的地址。 文件描述符&…

【Linux系統編程學習】 文件描述符

此為牛客網Linux C課程1.19課程筆記。 1. 文件描述符表 如圖&#xff0c;我們知道每個進程都有其虛擬地址空間&#xff08;0~4G&#xff09;&#xff0c;其中3 ~ 4G部分為內核區。進程的進程控制塊保存就在內核區&#xff0c;而PCB中維護一個打開文件描述符表&#xff0c;每個…

【Linux系統編程學習】Linux系統IO函數(open、read、write、lseek)

此為牛客網Linux C課程1.20課程筆記。 1.open函數 open函數有兩種&#xff0c;分別是打開一個已經存在的文件和創建并打開一個不存在的文件。 #include <sys/types.h> #include <sys/stat.h> #include <fcntl.h>// 打開一個已經存在的文件 int open(const…

【Linux系統編程學習】Linux進程控制原語(fork、exec函數族、wait)

此為牛客Linux C和黑馬Linux系統編程課程筆記。 1. fork函數 1.1 fork創建單個子進程 #include<unistd.h> pid_t fork(void);作用&#xff1a;創建一個子進程。 pid_t類型表示進程ID&#xff0c;但為了表示-1&#xff0c;它是有符號整型。(0不是有效進程ID&#xff0…

【Linux系統編程學習】匿名管道pipe與有名管道fifo

此為牛客Linux C和黑馬Linux系統編程課程筆記。 0. 關于進程通信 Linux環境下&#xff0c;進程地址空間相互獨立&#xff0c;每個進程各自有不同的用戶地址空間。任何一個進程的全局變量在另一個進程中都看不到&#xff0c;所以進程和進程之間不能相互訪問&#xff0c;要交換…

【Linux系統編程學習】信號、信號集以其相關函數

此為牛客Linux C和黑馬Linux系統編程課程筆記。 文章目錄0. 信號的概念1. Linux信號一覽表2. 信號相關函數3. kill函數4. raise函數5. abort函數6. alarm函數7. setitimer函數8. signal函數9. 信號集10. 自定義信號集相關函數11. sigprocmask函數12. sigpending函數13. sigacti…

【Linux系統編程學習】父進程捕獲SIGCHLD信號以處理僵尸進程

配合之前說過的sigaction函數和waitpid函數&#xff0c;我們可以解決子進程變成僵尸進程的問題。 先看如下示例程序&#xff1a; #include <sys/time.h> #include <sys/types.h> #include <stdio.h> #include <stdlib.h> #include <signal.h> …

【Linux系統編程學習】Linux線程控制原語

此為牛客Linux C課程筆記。 0. 關于線程 注意&#xff1a;LWP號和線程id不同&#xff0c; LWP號是CPU分配時間片的依據&#xff0c;線程id是用于在進程內部區分線程的。 1. 線程與進程的區別 對于進程來說&#xff0c;相同的地址(同一個虛擬地址)在不同的進程中&#xff0c;反…

【Linux網絡編程學習】預備知識(網絡字節序、IP地址轉換函數、sockaddr數據結構)

此為牛客Linux C課程和黑馬Linux系統編程筆記。 1. 網絡字節序 我們已經知道&#xff0c;內存中的多字節數據相對于內存地址有大端和小端之分。 磁盤文件中的多字節數據相對于文件中的偏移地址也有大端小端之分。網絡數據流同樣有大端小端之分&#xff0c;那么如何定義網絡數…

【Linux網絡編程學習】socket API(socket、bind、listen、accept、connect)及簡單應用

此為牛客Linux C課程和黑馬Linux系統編程筆記。 1. 什么是socket 所謂 socket&#xff08;套接字&#xff09;&#xff0c;就是對網絡中不同主機上的應用進程之間進行雙向通信的端點的抽象。 一個套接字就是網絡上進程通信的一端&#xff0c;提供了應用層進程利用網絡協議交換…

【Linux網絡編程學習】使用socket實現簡單服務器——多進程多線程版本

此為牛客Linux C課程和黑馬Linux系統編程筆記。 1. 多進程版 1.1 思路 大體思路與上一篇的單進程版服務器–客戶端類似&#xff0c;都是遵循下圖&#xff1a; 多進程版本有以下幾點需要注意&#xff1a; 由于TCP是點對點連接&#xff0c;服務器主進程連接了一個客戶端以后…

【Linux網絡編程學習】I/O多路復用——select和poll

此為牛客Linux C課程和黑馬Linux系統編程筆記。 0. I/O多路復用 所謂I/O就是對socket提供的內存緩沖區的寫入和讀出。 多路復用就是指程序能同時監聽多個文件描述符。 之前的學習中寫了多進程和多線程版的簡單服務器模型&#xff0c;但是有個問題&#xff1a;每次新來一個客…

【Linux網絡編程學習】I/O多路復用——epoll

此為牛客Linux C課程和黑馬Linux系統編程筆記。 1. 關于epoll epoll是Linux下多路復用IO接口select/poll的增強版本&#xff0c;它能顯著提高程序在大量并發連接中只有少量活躍的情況下的系統CPU利用率&#xff0c;因為它會復用文件描述符集合來傳遞結果而不用迫使開發者每次…

【Linux網絡編程學習】阻塞、非阻塞、同步、異步以及五種I/O模型

文章目錄1. 基本概念1.1 阻塞與非阻塞1.2 同步與異步1.3 為什么沒有“異步阻塞”2. 五種IO模型2.1 阻塞 blocking2.2 非阻塞 non-blocking2.3. IO復用&#xff08;IO multiplexing&#xff09;2.4 信號驅動&#xff08;signal-driven&#xff09;2.5 異步&#xff08;asynchron…

LRU緩存 數據結構設計(C++)

做LeetCode第146題LRU緩存&#xff0c;覺得收獲不小&#xff0c;特此記錄。 請你設計并實現一個滿足 LRU (最近最少使用) 緩存 約束的數據結構。 實現 LRUCache 類&#xff1a; LRUCache(int capacity) 以 正整數 作為容量 capacity 初始化 LRU 緩存。int get(int key) 如果關鍵…

STM32時鐘樹解析

本人之前其實也用STM32做過一些小東西&#xff0c;但因為時鐘的初始化一般是直接在SystemInit時鐘系統初始化函數里直接配置為72MHz&#xff0c;所以對于STM32的時鐘框圖并沒有怎么理會&#xff0c;今天剛好有空就重新看了一下并寫一篇博客記錄一下吧&#xff0c;以免以后又忘了…

S3C2440時鐘體系

S3C2440在默認情況下&#xff0c;整個系統全靠一個12MHz的外部晶振提供頻率來工作運行的&#xff0c;也就是說CPU、內存、UART、ADC等所有需要用到時鐘頻率的硬件都工作在12MHz下&#xff0c;但是通過查閱芯片手冊我們知道CPU時鐘最高可為400MHZ&#xff0c;那么怎么設置時鐘讓…

關于MCU、CPU擴展SDRAM的一個小知識

像上圖這種硬件電路圖上的16個數據位和我們在初始化SDRAM的時候設置的16位數據位寬是指我們讀寫SDRAM的時候可以同時讀寫16個數據位&#xff0c;數據線越多肯定越快&#xff0c;但是數據線也不可能無限增加&#xff0c;我們在程序里是可以讀寫8位&#xff0c;16位&#xff0c;3…

S3C2440擴展SDRAM

本文主要目的是記錄一下S3C2440擴展SDRAM的一些知識&#xff0c;方便以后查閱。 通過查閱手冊我們知道&#xff0c;2440有8個可以用來擴展內存的BANK&#xff0c;其中第6和第7還可用來擴展SDRAM 下面我們來看一下2440擴展SDRAM需要設置哪些寄存器。 一、BWSCON寄存器 該寄存器…