Makefile là một trong những công cụ không thể thiếu, giúp tự động hóa các tác vụ này, giảm thiểu lỗi và tiết kiệm thời gian cho các nhà phát triển. Bài viết dưới đây sẽ đi sâu vào khái niệm Makefile trong Linux, từ cú pháp cơ bản đến các ví dụ thực tế, giúp bạn hiểu rõ hơn về công cụ mạnh mẽ này để tối ưu hóa quy trình làm việc của mình.
Những điểm chính
- Định nghĩa Makefile: Giới thiệu khái niệm Makefile, vai trò trong việc tự động hóa biên dịch và quản lý dự án.
- Cách hoạt động của makefile: Giải thích cách Makefile hoạt động, tổ chức lệnh và quy tắc để thực thi các nhiệm vụ.
- Cú pháp của makefile: Hướng dẫn cú pháp cơ bản trong Makefile để tạo và quản lý quy trình build.
- Đặt mục tiêu (Targets): Giới thiệu cách đặt mục tiêu (targets) trong Makefile để thực thi các nhiệm vụ cụ thể.
- Wildcards – ký tự đại diện: Giải thích về ký tự đại diện trong Makefile giúp linh hoạt trong việc định nghĩa tệp và mục tiêu.
- Các quy tắc nâng cao: Giới thiệu các quy tắc nâng cao như static pattern rules và double-colon rules để tối ưu hóa Makefile.
- Điều kiện trong Makefiles: Cách sử dụng điều kiện kiểm tra giá trị của biến trong Makefile.
- Hàm trong Makefiles: Giới thiệu các hàm cơ bản và nâng cao như foreach, if, call, shell trong Makefile.
- Tính năng makefile khác: Trình bày một số tính năng bổ sung như multiline, .phony và .delete_on_error để tối ưu hóa Makefile.
- Biết đến Vietnix – Nhà cung cấp dịch vụ VPS linh hoạt và hiệu suất cao.
Makefile là gì?
Makefile là một tiện ích dạng dòng lệnh trên hệ điều hành Linux, giúp tự động hóa quá trình biên dịch chương trình, đặc biệt là các chương trình lớn. Lệnh xác định phần nào của chương trình cần được biên dịch lại khi có thay đổi ở một số file nguồn.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 81 Makefile là một tiện ích giúp tự động hóa quá trình biên dịch](https://image.vietnix.vn/wp-content/uploads/2025/02/makefile-la-gi.png)
Makefile sử dụng một file cấu hình (thường có tên “Makefile” hoặc “makefile”) chứa các quy tắc và lệnh cần thực thi. Các dự án mã nguồn mở thường dùng make để biên dịch chương trình thực thi và sử dụng lệnh make install
để cài đặt. Trong bài viết này, mình sẽ tập trung vào ngôn ngữ C/C++, vì ngôn ngữ này thường được biên dịch trực tiếp, trong khi các ngôn ngữ khác có thể sử dụng công cụ biên dịch riêng.
Cú pháp makefile trong Linux
Mỗi Makefile gồm một tập hợp các rule và mỗi rule được hiểu như sau:
<targets>: <prerequisite>
<command>
<command>
<command>
Trong đó có ba thành phần chính:
- <target>: Chỉ định tên file, phân chia bằng dấu cách. Mỗi rule chỉ dành cho 1 target.
- <prerequisite>: Tên các file mà mục tiêu phụ thuộc vào. Các file này buộc phải tồn tại trước khi các lệnh tạo mục tiêu được thực thi.
- <command>: Các hành động hoặc bước để tạo ra mục tiêu. Bắt buộc phải bắt đầu mỗi lệnh bằng một ký tự tab (không phải dấu cách). Nếu dùng dấu cách, make sẽ báo lỗi.
Phiên bản của makefile
Hầu hết các lệnh được sử dụng có liên quan makefile đều có thể hoạt động trên cả phiên bản 3 và 4. Để biết được phiên bản hiện tại, bạn gõ lệnh sau:
make - version
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 82 Xem phiên bản lệnh make](https://static.vietnix.vn/wp-content/uploads/2025/01/1-make-version.webp)
Cách thức hoạt động của makefile
Makefile tự động biên dịch các source file cần biên dịch dựa trên việc phát hiện các thay đổi. Với ngôn ngữ thông dịch, việc biên dịch lại là không cần thiết vì chương trình luôn sử dụng phiên bản mới nhất của file. Makefile hoạt động dựa trên biểu đồ phụ thuộc giữa các file. Nếu một file phụ thuộc (dependency) bị thay đổi, file sử dụng các phụ thuộc đó cũng sẽ được biên dịch lại.
Đặc biệt, khi sử dụng Makefile để biên dịch các dự án lớn hoặc xử lý đa nhiệm, đòi hỏi môi trường máy chủ có tốc độ cao và khả năng vận hành ổn định. Với dịch vụ VPS NVMe của Vietnix, bạn sẽ được trang bị 100% ổ cứng NVMe tốc độ cao và CPU Intel Platinum thế hệ mới, cho tốc độ xử lý nhanh gấp 10 lần so với SSD thông thường. Dịch vụ VPS còn kết hợp với băng thông 400 Mbps, cam kết uptime 99.9%, Vietnix đảm bảo hiệu suất tối ưu, giúp bạn rút ngắn thời gian biên dịch và xử lý tác vụ phức tạp.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 83 Cách hoạt động của Make](https://static.vietnix.vn/wp-content/uploads/2025/01/2-how-to-make-work.webp)
Hiển thị “Hello World”
Trước khi tiếp tục, bạn hãy thử thực hiện một ví dụ về makefile để hiểu cách viết và thực thi make. Nếu máy tính của bạn chưa có lệnh make, hãy cài đặt như sau:
sudo apt install make
Bạn tạo một file mới và thêm nội dung vào file đó, tên file này phải là “Makefile” hoặc “makefile”.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 84 Đặt tên file](https://static.vietnix.vn/wp-content/uploads/2025/01/3-makefile.webp)
Sau đó bạn hãy nhập lệnh make
trong Terminal để thực thi file vừa tạo.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 85 Thực thi make file](https://static.vietnix.vn/wp-content/uploads/2025/01/4-execute-file.webp)
Các ví dụ cho người mới
Bạn đã nắm được cách viết và thực thi lệnh make. Bây giờ sẽ đến bước tìm hiểu kiến thức cơ bản, 3 thành phần chính: target – prerequisite – command thông qua vài ví dụ đơn giản. Bạn hãy thử tạo một “makefile” có 3 rule riêng biệt mà khi thực thi sẽ tạo thành một chương trình có tên là test qua các bước sau:
- Make đưa ra test là target, nó sẽ chọn tìm kiếm mục tiêu này.
- test sẽ yêu cầu test.o, makefile sẽ chuyển sang tìm kiếm “test.o”.
- test.o yêu cầu test.c để tìm kiếm mục tiêu này.
- test.c không có phụ phuộc nên sẽ chạy lệnh
echo
. - Lệnh
cc -c
sẽ chạy khi tất cả phần phụ thuộc của test.o hoàn tất. - Lệnh
cc
chạy ngay sau đó.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 86 Ví dụ cơ bản về makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/5-basic-example.webp)
Tiếp theo, bạn cho thực thi makefile test với lệnh sau để kiểm tra kết quả:
make test
Ở ví dụ khác, bạn sẽ chỉ có 1 file tên a_file, khi target được chỉ định sẽ là chính là file này.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 87 Chỉ định thực hiện về a_file](https://static.vietnix.vn/wp-content/uploads/2025/01/6-example-1.webp)
Khi bạn thực thi Makefile, bạn sẽ nhận được kết quả như sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 88 Thêm lệnh mới vào makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/7-thuc-thi-ex1.webp)
Sau đó, bạn tiếp tục thêm vào file lệnh tạo file mới.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 89 Thêm lệnh mới vào makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/8-them-lenh-vao-ex1.webp)
Bạn thực thi file và nhận được kết quả sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 90 Thực thi makefile và xem kết quả](https://static.vietnix.vn/wp-content/uploads/2025/01/8a-thuc-thi-ex1.webp)
Kết quả hiển thị không có gì đặc biệt, bên cạnh đó bạn đã tạo file có tên a_file mà bạn đang nhìn thấy qua lệnh ls.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 91 Cập nhật make file](https://static.vietnix.vn/wp-content/uploads/2025/01/8b-cap-nhat-a_file.webp)
Bạn hãy tăng độ phức tạp lên một chút bằng cách cho a_file phụ thuộc vào b_file. Thông thường, mục tiêu (target) sẽ kiểm tra danh sách các phụ thuộc. Nếu bất kỳ phụ thuộc (dependency) nào có mốc thời gian cũ hơn mục tiêu, make sẽ thực thi lệnh để cập nhật chúng, sau đó xử lý phần còn lại. Ngược lại, nếu tất cả các phụ thuộc đều tồn tại và không có thay đổi nào, make sẽ bỏ qua việc thực thi lệnh, vì các mục tiêu đã được cập nhật và không cần biên dịch lại.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 92 Cho a_file phụ thuộc b_file](https://static.vietnix.vn/wp-content/uploads/2025/01/9-a_file-depend-on-b_file.webp)
Khi bạn thực thi lại file thì kết quả sẽ như sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 93 Thực thi makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/10-execute-makefile.webp)
Đặt mục tiêu
Nếu bạn muốn đặt nhiều mục tiêu (target) và chạy tất cả thì bạn chỉ cần gấn tất cả thành target như sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 94 Đặt mục tiêu vào makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/11-set-target.webp)
Bạn tiến thành chạy lệnh make và nhận kết quả sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 95 Thực thi makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/12-execute-makefile.webp)
Ngoài ra, bạn còn có thể đặt nhiều target (Multiple targets) nằm chung một rule, lệnh sẽ thực thi chạy từng target đã chỉ định. Cụ thể bạn dùng biến tự động là $@ để chứa tên target.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 96 Đặt nhiều mục tiêu](https://static.vietnix.vn/wp-content/uploads/2025/01/13-set-multi-target.webp)
Kết quả khi thực thi lệnh make
như sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 97 Thực thi makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/14-execute-makefile.webp)
Biến (Variables)
Biến trong Make chỉ có định dạng chuỗi thông thường mà không thể sử dụng kiểu biến khác như integer (số nguyên) hay float (số thập phân). Để hiểu hơn, bạn có thể xem qua ví dụ sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 98 Đặt biến trong makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/15-variable.webp)
Bạn hãy thực thi makefile và nhận được kết quả sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 99 Hiển thị biến trong makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/16-execute-makefile.webp)
Ở một ví dụ tiếp theo, biến tham chiếu sử dụng $() hoặc ${}:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 100 Sử dụng $() và ${} cho biến tham chiếu](https://static.vietnix.vn/wp-content/uploads/2025/01/17-and-.webp)
Trong ví dụ này bạn sẽ thấy kết quả khi gán biến như sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 101 Thực thi file make](https://static.vietnix.vn/wp-content/uploads/2025/01/18-execute-file.webp)
Flavors và modification
Trong Makefile có 2 kiểu biến flavor như sau:
- = (recursive): Giá trị của biến chỉ được tính toán (đánh giá) khi biến đó được sử dụng trong một lệnh.
- := (simply expanded): Chỉ những giá trị đã được định nghĩa tại thời điểm khai báo mới được sử dụng.
Dưới đây là ví dụ giúp bạn hiểu hơn về 2 kiểu biến này:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 102 Sử dụng biến flavor](https://static.vietnix.vn/wp-content/uploads/2025/01/19-set-flavor-variable.webp)
Bạn thực thi makefile và sẽ thấy kết quả sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 103 Thực thi makefilfe](https://static.vietnix.vn/wp-content/uploads/2025/01/20-execute-file.webp)
Biến mở rộng giúp bạn thêm biến mới như ví dụ sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 104 Mở rộng biến](https://static.vietnix.vn/wp-content/uploads/2025/01/21-extend-variable.webp)
Bạn có thể kết hợp 2 biến flavor để tạo kết quả mới.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 105 Thực thi file](https://static.vietnix.vn/wp-content/uploads/2025/01/22-execute-file.webp)
Bên cạnh đó, còn một biến nữa là ?=, được dùng để gán biến nếu các biến đó chưa được thiết lập, bạn có thể xem qua ví dụ sau.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 106 Sử dụng phép gán biến "?="](https://static.vietnix.vn/wp-content/uploads/2025/01/23-variable-.webp)
Khi tiến hành thực thi makefile, bạn sẽ nhận được kết quả sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 107 Thực thi makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/24-execute-file.webp)
Tình huống tiếp theo là việc đưa khoảng trắng vào trong biến. Bạn hoàn toàn có thể sử dụng biến có khoảng trắng, nhưng chỉ có thể giữ khoảng trắng ở cuối dùng, ở đầu dòng sẽ bị xóa. Do đó nếu bạn cần khoảng trắng này, hãy tạo biến tên là $(nullstring).
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 108 Sử dụng biến nullstring](https://static.vietnix.vn/wp-content/uploads/2025/01/25-nullstring.webp)
Bạn tiến hành thực thi makefile và nhận được kết quả sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 109 Thực thi file](https://static.vietnix.vn/wp-content/uploads/2025/01/26-execute-file.webp)
Nếu trong trường hợp bạn không khai báo, định nghĩa biến thì make sẽ trả về chuỗi rỗng. Nhưng ở đây, mình sẽ cho hiển thị giá trị của biến tên vietnix, mà không cần khai báo hay gán bất kỳ thứ gì vào biến này, nghĩa là bạn không cần định nghĩa biến.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 110 Không khai báo biến](https://static.vietnix.vn/wp-content/uploads/2025/01/27-no-variable-defined.webp)
Khi thực thi lệnh make
, vì lí do trên nên hệ thống sẽ trả về kết quả trống.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 111 Thực thi makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/28-execute-file.webp)
Đối số lệnh và ghi đè giá trị
Bạn có thể ghi đè các biến bằng cách sử dụng override
như ví dụ sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 112 29 Command line arguments and override](https://static.vietnix.vn/wp-content/uploads/2025/01/29-Command-line-arguments-and-override.webp)
Kết quả như sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 113 Tiến hành thực thi make và trả về kết quả](https://static.vietnix.vn/wp-content/uploads/2025/01/30-execute-makefile.webp)
Danh sách command và “define”
Có sự hiểu lầm define
là một hàm. Tuy nhiên, define
chỉ là danh sách các lệnh. Bạn có thể hiểu hơn ở ví dụ sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 114 Sử dụng define trong make](https://static.vietnix.vn/wp-content/uploads/2025/01/31-define.webp)
Kết quả sau khi thực hiện makefile:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 115 Kết quả thực thi makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/32-execute-makefile.webp)
Chỉ định biến cho mục tiêu
Bạn cũng có thể gán biến cho target cụ thể tương tự ví dụ sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 116 Chỉ định biến cho mục tiêu](https://static.vietnix.vn/wp-content/uploads/2025/01/33-set-variable-for-target.webp)
Sau khi bạn thực thi, kết quả trả về như sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 117 Thực thi makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/34-execute-makefile.webp)
Chỉ định biến cho pattern
Các biến cũng có thể được thiết lập cho các pattern cụ thể như ví dụ bên dưới:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 118 Chỉ định biến cho pattern](https://static.vietnix.vn/wp-content/uploads/2025/01/35-set-variable-for-pattern.webp)
Kết quả thực thi makefile như sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 119 Kết quả thực thi make file](https://static.vietnix.vn/wp-content/uploads/2025/01/36-execute-makefile.webp)
Biến tự động
Trên thực tế, có khá nhiều biến tự động mà bạn có thể áp dụng trong makefile nhưng chỉ số ít là hiển thị lên màn hình.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 120 37 automatic variable](https://static.vietnix.vn/wp-content/uploads/2025/01/37-automatic-variable.webp)
Kết quả trả về như sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 121 Thực thi biến tự động](https://static.vietnix.vn/wp-content/uploads/2025/01/38-execute-makefile-2.webp)
Wildcards – Ký tự đại diện
Bạn có thể dùng * hoặc % để làm ký tự wildcard, nhưng cả 2 lại có nghĩa khác nhau, bạn hãy xem ví dụ bên dưới để thấy sự khác biệt này.
- Kí tự * : Có chức năng là dò trong filesystem để tìm ra file có tên phù hợp.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 122 Kí tự đại diện *](https://static.vietnix.vn/wp-content/uploads/2025/01/39-wildcard-.webp)
- Kí tự % : Kí tự này dùng trong các tình huống sau.
- Trùng khớp 1 hoặc nhiều ký tự (gọi là stem).
- Lấy stem đó và thay bằng 1 chuỗi.
- Dùng trong rule định nghĩa (definition) và các hàm cụ thể.
Fancy rules – Các quy tắc nâng cao
Quy tắc ngầm
Khi make biên dịch chương trình c, lệnh sử dụng các quy tắc tự động và gọi các rule này là “quy tắc ngầm” này. Sau đây là danh sách các quy tắc ngầm:
- Compiling chương trình C: “n.o” được tạo tự động “n.c” với lệnh dạng của giá trị $(CC) -c $(CPPFLAGS) $(CFLAGS)
- Compiling chương trình C++: “n.o” được tạo tự động từ “n.cc” hoặc “n.cpp” với lệnh của dạng giá trị $(CXX) -c $(CPPFLAGS) $(CXXFLAGS).
- Liên kết một object file: “n” được tạo tự động từ “n.o” bằng cách thực thi lệnh $(CC) $(LDFLAGS) n.o $(LOADLIBES) $(LDLIBS).
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 123 icon](https://image.vietnix.vn/wp-content/uploads/2024/09/book-open-yellow.png)
Ví dụ: Để xây dựng chương trình C, mà không cần chỉ dẫn cách biên dịch cho make. Bạn thực hiện như sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 124 Liên kết một object file](https://static.vietnix.vn/wp-content/uploads/2025/01/40-link-object-file.webp)
Quy tắc pattern tĩnh
Quy tắc này là một cách khác để bạn có thể viết ít hơn trong lệnh Makefile, cú pháp như sau:
targets...: target-pattern: prereq-patterns ...
commands
Ý tưởng ban đầu là target chỉ định sẽ trùng khớp với target-pattern (thông qua kí tự đại diện %), bạn hãy xem qua ví dụ sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 125 Quy tắc pattern tĩnh](https://static.vietnix.vn/wp-content/uploads/2025/01/41-Static-pattern-rules.webp)
Quy tắc pattern tĩnh và bộ lọc
Bộ lọc có thể dùng trong quy tắc pattern tĩnh để so trùng với các file chính xác. Ví dụ: Tạo phần mở rộng .raw và .result.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 126 Bộ lọc và quy tắc pattern tĩnh](https://static.vietnix.vn/wp-content/uploads/2025/01/42-Static-pattern-rules-and-filters.webp)
Quy tắc pattern
Quy tắc này được sử dụng tốt nhất trong 2 trường hợp sau:
- Xác định các quy tắc ngầm của riêng bạn.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 127 Quy tắc ngầm tạo bới user](https://static.vietnix.vn/wp-content/uploads/2025/01/43-pattern-rule-1.webp)
- Dạng đơn giản hơn của quy tắc pattern tĩnh.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 128 Quy tắc pattern tĩnh](https://static.vietnix.vn/wp-content/uploads/2025/01/44-pattern-rule-2.webp)
Quy tắc hai chấm đôi
Quy tắc này rất ít được sử dụng, chức năng của double-colon cho phép nhiều rule được định nghĩa cho cùng target. Khi sử dụng cần phải cẩn thận nhầm lẫn mới dấu đơn, cảnh báo lỗi sẽ xuất hiện và bỏ qua file đầu tiên.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 129 Quy tắc dấu hai chấm đôi](https://static.vietnix.vn/wp-content/uploads/2025/01/45-double-colon.webp)
Kết quả trả về:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 130 Thực thi makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/46-execute-filemake.webp)
Lệnh và thực thi
Lệnh echoing/silencing
Để dừng lệnh hiển thị như lệnh echo, bạn thêm kí hiệu @ (at the rate) trước lệnh đó. Bên cạnh đó, bạn cũng dùng được lệnh make
với tùy chọn -s
để thêm @ trước mỗi dòng.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 131 Lệnh echo và kí hiệu sliencing](https://static.vietnix.vn/wp-content/uploads/2025/01/47-echoing-silencing.webp)
Kết quả: Bạn sẽ thấy được dòng echo đầu đã bị chặn không cho hiển thị trên màn hình mà chỉ dòng echo thứ hai mới được phép.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 132 Thực thi makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/48-execute-amkefile.webp)
Shell mặc định
Khi nhắc về shell trên Linux, thì shell mặc định của makefile nằm ở /bin/sh nhưng bạn lại có thể thay đổi khi sử dụng biến SHELL như ví dụ sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 133 Thay đổi Shell mặc định](https://static.vietnix.vn/wp-content/uploads/2025/01/51-change-default-shell.webp)
Kết quả như sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 134 Thực thi makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/52-execute-makefile.webp)
Xử lý lỗi
Bạn sẽ xử lý lỗi khác nhau bằng cách dùng các kí tự dưới đây:
- -k : Tiếp tục thực thi kể cả gặp lỗi.
- – : Dùng trước dòng lệnh để ẩn lỗi đi.
- -i : HIển thị chi tiết có những gì diễn ra ở mỗi lệnh.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 135 Xử lý lỗi](https://static.vietnix.vn/wp-content/uploads/2025/01/53-error-handling.webp)
Kết quả trả về như sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 136 Makefile xử lý lỗi](https://static.vietnix.vn/wp-content/uploads/2025/01/54-execute-makefile.webp)
Sử dụng đệ quy make
Nếu bạn muốn gọi đệ quy một makefile thì bạn hãy dùng biến đặc biệt là $(MAKE) thay vì make. Vì biến sẽ bỏ qua make flag và không ảnh hưởng bởi chính biến đó. Bạn có thể tham khảo ví dụ sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 137 Lệnh make có đệ quy](https://static.vietnix.vn/wp-content/uploads/2025/01/55-corrupt-or-terminate-make.webp)
Kết quả trả về như sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 138 Thực thi makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/56-execute-makefile.webp)
Dùng export gọi makefile đệ quy
Có một cách khác để gọi makefile đệ quy là dùng export. Directive này sẽ lấy 1 biến và cho biến đó truy cập được vào lệnh hiện có trong make, được gọi là submake.
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 139 Dùng export để gọi makefile đệ quy](https://static.vietnix.vn/wp-content/uploads/2025/01/57-using-export.webp)
Kết quả như sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 140 Thực thi makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/58-execute-makefile.webp)
Điều kiện trong Makefiles
Mệnh đề điều kiện if-else dường như đã quen thuộc với mọi người, trong makefile thì logic của hàm này cũng không có gì thay đổi. Chỉ có cú pháp sẽ khác một chút so với mệnh đề if-else ở ngôn ngữ khác. Bạn có thể xem qua ví dụ sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 141 Cú pháp mệnh đề if else trong makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/59-if-else.webp)
Kết quả trả về như sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 142 Thực thi makefile có if-else](https://static.vietnix.vn/wp-content/uploads/2025/01/60-execute-makefile.webp)
Hàm trong Makefiles
Hàm cơ bản
Mục đích chính của các hàm là xử lý văn bản nhưng bạn vẫn có thể tạo các hàm riêng của mình bằng việc dùng lệnh gọi hàm tích hợp. Ví dụ:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 143 Hàm cơ bản](https://static.vietnix.vn/wp-content/uploads/2025/01/63-basic-function.webp)
Kết quả trả về:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 144 Thực thi makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/64-execute-makefile.webp)
Thay thế chuỗi
Hàm này tìm các từ được phân tách bằng khoảng trống trùng khớp với mẫu (pattern), thay thế chúng bằng từ được chỉ định. Ví dụ:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 145 Thực hiện thay thế chuỗi](https://static.vietnix.vn/wp-content/uploads/2025/01/65-replace-string.webp)
Kết quả như sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 146 Tiến hành thực thi makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/66-execute-makefile.webp)
Hàm Foreach
Chức năng của hàm là chuyển đổi một danh sách các từ thành một danh sách khác. Cú pháp sẽ như sau:
$(foreach var, <list>, <text>)
Ví dụ:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 147 Sử dụng hàm foreach](https://static.vietnix.vn/wp-content/uploads/2025/01/67-foreach-function.webp)
Kết quả trả về như sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 148 Thực thi makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/68-execute-makefile.webp)
Hàm If
Hàm If sẽ kiểm tra đối số đầu tiên có rỗng hay không. Khi kết quả không rỗng, thì hàm sẽ chuyển sang kiểm tra đối số thứ hai, thứ ba,…Ví dụ:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 149 Hàm if kiểm tra đối số](https://static.vietnix.vn/wp-content/uploads/2025/01/69-if-function-check-empty.webp)
Kết quả trả về:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 150 Thực thi makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/70-execute-makefile.webp)
Hàm call
Như đã đề cập ở trên, hàm call tích hợp được sử dụng để tạo các hàm tùy chỉnh (custom). Bạn sẽ tạo biến để định nghĩa hàm tùy chỉnh, các tham số phải sử dụng như $(0), $(1),… Cú pháp của hàm là:
$(call <variable>, <parameter>, <parameter>)
Ví dụ:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 151 Sử dụng hàm call trong makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/71-call-function.webp)
Kết quả như sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 152 Kết quả thực thi make file](https://static.vietnix.vn/wp-content/uploads/2025/01/72-execute-makefile.webp)
Hàm shell
Hàm này cho phép bạn chạy các lệnh trên Terminal nhưng sẽ thay thế việc xuống dòng mới bằng khoảng trắng. Bạn hãy xem ví dụ sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 153 Sử dụng hàm shell](https://static.vietnix.vn/wp-content/uploads/2025/01/73-shell-function.webp)
Khi bạn thực hiện makefile, kết quả trả về như sau:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 154 Thực thị makefile](https://static.vietnix.vn/wp-content/uploads/2025/01/74-execute-makefile.webp)
Tính năng makefile bổ sung khác
Bên cạnh đó, makefile còn một số tính năng bổ sung sau:
Multiline
Dấu \ mang lại khả năng sử dụng nhiều dòng khi lệnh được viết quá dài, bạn sẽ nhìn thấy trọn vẹn câu lệnh khi hiển thị. Ví dụ:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 155 Dùng \ để ngắt xuống dòng mới](https://static.vietnix.vn/wp-content/uploads/2025/01/75-multiline.webp)
.phony
.PHONY được sử dụng để khai báo mục tiêu (target) trong makefile, không đại diện cho một file thật trên filesystem, mà thay vào đó chỉ là một tên biểu tượng được sử dụng để chạy một tập hợp các lệnh. Ví dụ:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 156 Sử dụng .phony feature](https://static.vietnix.vn/wp-content/uploads/2025/01/76-phony-feature.webp)
.delete_on_error
.DELETE_ON_ERROR yêu cầu make tự động xóa các file trung gian hoặc file kết quả (intermediate or target files) nếu có lỗi xảy ra trong quá trình xây dựng target. Lệnh này tránh để lại các file không hoàn chỉnh nếu quá trình xây dựng bị lỗi, giúp tránh tình trạng sử dụng lại các file hỏng trong lần xây dựng sau. Ví dụ:
![Tổng quan về Makefile là gì? Cách viết makefile đơn giản 157 Sử dụng .delete_on_error](https://static.vietnix.vn/wp-content/uploads/2025/01/77-delete-on-error.webp)
Vietnix – Nhà cung cấp dịch vụ VPS linh hoạt và hiệu suất cao
Vietnix cung cấp dịch vụ VPS Việt Nam với hạ tầng hiện đại và khả năng tùy biến tối ưu, đáp ứng nhu cầu đa dạng từ cá nhân đến doanh nghiệp. Hệ thống đạt các tiêu chuẩn bảo mật quốc tế như ISO 27001:2022 và ISO 9001:2015, đảm bảo dữ liệu luôn được bảo vệ chặt chẽ. Khách hàng có toàn quyền quản trị máy chủ, dễ dàng thực hiện các thao tác như cài đặt hệ điều hành, theo dõi tài nguyên hay sao lưu dữ liệu từ giao diện quản lý trực quan. Đặc biệt, quy trình kích hoạt và nâng cấp hoàn toàn tự động giúp bạn nhanh chóng sử dụng dịch vụ chỉ sau vài thao tác đơn giản.
Thông tin liên hệ:
- Hotline: 18001093
- Email: sales@vietnix.com.vn
- Địa chỉ: 265 Hồng Lạc, Phường 10, Quận Tân Bình, Thành Phố Hồ Chí Minh.
- Website: https://vietnix.vn/
Makefile là công cụ mạnh mẽ giúp tự động hóa quá trình biên dịch và quản lý dự án trên Linux. Hiểu rõ cách viết và sử dụng Makefile không chỉ giúp bạn tăng hiệu quả công việc mà còn đảm bảo tính nhất quán trong quá trình phát triển phần mềm.