"Foreword" in the Linux embedded development which I have contacted, mostly uses the C language, uses the makefile file to compile the source file to build the executable file. This article describes how a small C project can write makefile documents from a personal experience.
First, gcc command
From the point of view, the GCC command and the makefile function are the same, that is, the source file compiled after the generation of executable files or. o binary files. There are many additional parameters in the GCC command, and this article only describes the following simple and common methods:
There are HELLOWORLD.C files as follows:
#include <stdio.h>int main () { printf ("helloworld!\n") ; return 0 ;}
With the following GCC command, the a.out executable is generated in the same file directory, and the file is run in terminal to print out the helloworld! on the screen:
$ gcc helloworld.c
Using the following GCC command, the HELLOWORLD.O binaries are generated under the same file directory, which can be used to connect files:
$ gcc -C HELLOWORLD.C
If you want to generate a specific name for an executable file, you can use the following GCC command, which will generate the HelloWorld executable, which differs from the a.out executable file, which can be printed out helloworld! when TERMIANL executes it:
$ gcc helloworld.c-o HelloWorld
The above three kinds of gcc command, the main difference is that the parameter is different, the difference between-C and-O is that the-c only compile does not connect, so only generate. o binary file,-O is the specified name output executable file. For single or several source files, use the GCC command, but once the files have dependencies, the order in which the GCC commands are executed is required, otherwise the project cannot be compiled sequentially, which is a disadvantage of the GCC command. What distinguishes makefile from the GCC command is that it can specify dependencies between files, as well as adding dependent library files and header files.
If you want to reference a header file in another directory, its GCC command is as follows, using the-I parameter:
$ gcc -i/ycl/include/helloworld.c-o HelloWorld
If you want to reference a library file under another directory, such as libmlib.so, its GCC command is as follows, with the parameter of-L:
$ gcc -l/ycl/lib–lmlib helloworld.c-o HelloWorld
Ii. Brief Grammar of Makefile
The use of makefile is to tell the editor what rules this project compiles and links to, and running make commands requires makfile files as support.
To understand makefile, the key is to understand its core syntax (from the blog http://blog.csdn.net/liang13664759/article/details/1771246):
Target ...: Prerequisites ...
Command
...
...
Target is a destination file, which can be either an object or an executable file. It can also be a label, which is described in the following "pseudo-targets" section for labels.
Prerequisites is to generate the desired file or target for that target.
command is what the make needs to execute. (Arbitrary shell Command)
This is a file dependency, that is, target one or more of the destination files depend on the files in the prerequisites, and their generation rules are defined in the command. White point is that if more than one file in the prerequisites is newer than the target file, command-defined commands are executed. This is the rule of makefile. This is the core content of makefile.
The sample code is as follows:
CXX = g++= -o2-g-wall-fmessage-length=0= 'pkg-config --cflags LCM ' Ldflags= 'pkg-config --Libs LCM ' -= dsrc_module.o lcmhandler.o = dsrc_module$ (TARGET): $ (OBJS) -o [email protected] $^ $ (ldflags)
Dsrc_module.o:dsrc_module.cpp
$ (CXX) $ (CFLAGS)-I.-O [email protected]-C $<
Lcmhandler.o:lcmhandler.cpp
$ (CXX) $ (CFLAGS)-I.-O [email protected]-C $<
Udphandler.o:udphandler.cpp
$ (CXX) $ (CFLAGS)-I.-O [email protected]-C $<
all:$ (TARGET)
Clean
Rm-f $ (OBJS) $ (TARGET)
The variable is present in the sample code, and the variable in makefile is used with a $ (variable) method, such as $ (TARGET), which represents Dsrc_module. The purpose of the makefile is to generate an executable named DSRC_ module, which is the $ (TARGET), and its dependent file is $ (OBJS) for the DSRC_MODULE.O, LCMHANDLER.O, and udphandler.o three files. Since none of the three files were generated, a compilation is required for each file, so there are three. o files for the target makefile statement.
The special characters are described as follows: [email protected] Target file, $^--all dependent files, $<--the first dependent file. For example, in the code below, [email protected] represents dsrc_module.cpp,$< for the first dependent file, which is dsrc_module.cpp.
Dsrc_module.o:dsrc_module. CPP -I.-o [email protected]-C $<
Iii. Preparation of Makefile
Using Eclipse with the CDT plugin, you can directly generate the Makefile project for the HelloWorld project, with the makefile content as follows:
Cxxflags = -o2-g-wall-fmessage-length=0= = = example$ (TARGET ): $ (OBJS) -o $ (target) $ (OBJS) $ (LIBS) All: $ (target) Clean: RM -F $ ( OBJS) $ (TARGET)
Where cxxflags is a compiler parameter variable, CXX is a makefile built-in variable, cxx default represents g++ (C + + compiler). This makefile has two functions: ① compile code, compile example.c into EXAMPLE.O and link it to example executable, ② Purge project, use make when project needs to be recompiled or collated The clean command clears the names in the raw OBJS and target variables.
In the above code, the dependent file does not have a. c file, because the makefile auto-derivation feature is used here, as long as the dependency relationship has an. o file, it automatically adds the same name as the. c file as a dependent file and is automatically deduced by $ (CXX)-O example.o to $ ( CXX)-O example.c.
$ (target): $ (OBJS) -o $ (target) $ (OBJS) $ (LIBS)
Based on the makefile file above, if you need to add a new. C and. h file at this time, then change the contents of OBJS, such as add test.c file, the code is as follows (note that before the TEST.O can not add space, the need for the TAB key):
Cxxflags = -o2-g-wall-fmessage-length=0= example.o == example$ (target): $ (OBJS) -o $ (TARGET) $ (OBJS) $ (LIBS) All: $ (target) Clean: RM -F $ (OBJS) $ (TARGET)
If you need to add a header file, simply add and modify the following code:
Header_dir =/home/duser/dot3 $ (target): $ (OBJS) -O $ (TARGET) $ (OBJS) $ (LIBS)-I $ (header_dir)
If you need to add a library file, you need two variables, ldflags---equivalent to the path of the library, LIBS---the library file to be linked. Just add and modify the following code:
Ldflags + =-l/+ =-ltest$ (target): $ ( objs)-o $ (target) $ (OBJS)-I $ (header_dir) $ (LDFLGS) $ ( LIBS)
Makefile writing of small C + + projects