Compilation of C-language multi-Files and application of makefile in Linux

Source: Internet
Author: User

1. About compiling and linking

In general, whether C, C + +, the first to compile the source file into an intermediate code file, under Windows is the. obj file, under Unix is the. o file, the object file, which is called compilation (compile). And then the large number of object file synthesis execution file, this action is called link.

That is, the source file (. c file or. cpp file) First generates an intermediate target file, and the execution file is generated by the intermediate target file. At compile time, the compiler detects only the program syntax, and whether the function or variable is declared. If the function is not declared, the compiler will give you a warning, but you can generate an object File. When linking a program, the linker will look for the implementation of the function in all object file, and if not, then the link error code (Linker error) will be reported.

2. Compiling links using commands

If you compile with commands, the process is cumbersome. If I had three. h header files and four. C code files. First put these seven files in a folder (here only simple application, so put in a folder, later slowly pits) such as.

Next, open the terminal and go to this folder.

Then in the terminal input

  

GCC---c ccc.c

This completes the compilation of four files, viewing the file will appear four. o Files ()

  

Follow the link. In the terminal input

GCC MAIN.O aaa.o bbb.o ccc.o-o Main

You can generate the executable file, main

  

This executes./main can be.

The entire execution process is as follows:

  

3. Compiling links with make

Although the above approach can be implemented, it is particularly troublesome to recompile the links as long as the files are modified. Use makefile to achieve more ingenious.

First out of a way, if only to execute their own code can look first, the back of the pit slowly fill.

objects ==$(objects)    -O-Edit $(objects) main.o:main.c  aaa.o:aaa.c   AAA.HBBB.O:BBB.C   bbb.hccc.o:ccc.c   ccc.h.phony:cleanclean:    

This can be run directly, I have just generated the compiled link file is deleted and then rerun

If Makefile:3 appears in make: * * * Missing separator: The reason is that the TAB key is missing, and each command needs a TAB key when it executes.

That's it, as with the results above, if you want to modify the contents of the file, no matter how many changes, do the following make on the line. Let's look at the usage of make in detail.

3.1 About make

When the make command executes, a makefile file is required to tell the make command what to do to compile and link the program (the makefile file creates a new line, and the name is best used with makefile).

First, we use an example to illustrate Makefile's writing rules. Using the example above, in this example, our project has 4 C files, and 3 header files, we are going to write a makefile to tell the make command how to compile and link the several files. Our Rules are:

1. If the project has not been compiled, all of our C files will be compiled and linked.

2. If some C files of this project are modified, then we only compile the modified C file and link the target program.

3. If the header file for this project is changed, then we need to compile the C file referencing the header files and link to the target program.

As long as our makefile is well written and all of this is done with just one make command, the make command automatically and intelligently determines which files need to be recompiled according to the current file modification, compiling the required files and linking the target program.

Rules for 3.2Makefile

  target...: Prerequisites ... (Preliminary knowledge, prerequisites)

Command (command)

...

...
-------------------------------------------------------------------------------

Target is a destination file, which can be either an object or an executable file.

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.

As an example, the example above can be implemented as follows:

edit:main.o aaa.o bbb.o ccc.o      -o edit main.o aaa.o bbb.o ccc.o main.o:main.c      -c main.caaa.o:aaa.c   AAA.h    -c AAA.CBB B.O:BBB.C   BBB.h    -c bbb.cccc.o:ccc.c   CCC.h    -C Ccc.cclean:    

The backslash (\) is the meaning of the newline character (none above). This makes the makefile easier to read. We can save this content in a file named "Makefile" or "makefile", and then enter the command "make" directly in the directory to generate the Execute file edit. If you want to delete the execution file and all the intermediate target files, simply execute "make clean".

In this makefile, the target file contains: Execute file Edit and intermediate target file (*.O), and the dependent file (prerequisites) is the. c file and the. h file after the colon. Each of the. o files has a set of dependent files, and these. o files are also dependent files that execute file edit. Dependency is essentially a description of which files are generated by the target file, in other words, which files are updated by the target file.

After defining the dependencies, the subsequent line defines how to generate the operating system commands for the target file, so be sure to start with a TAB key . Make and no matter how the command works, he just executes the defined command. Make compares the modified date of the targets file and the prerequisites file, and if the date of the prerequisites file is newer than the date of the targets file, or target does not exist, then make executes the subsequent defined command.

to illustrate the point is that clean is not a file, it is just an action name, a bit like the C language of lable, its colon after nothing, then make will not automatically find its dependencies, will not automatically execute the commands defined later. To execute subsequent commands (not only for clean, other lable also apply), it is necessary to clearly indicate the name of the lable after the make command. Such a method is very useful, we can in a makefile to define the unused compilation or compiler-independent commands, such as program packaging, program backup, and so on.

using variables in 3.3makefile

   In the example above, let's take a look at the rules of Edit:

EDIT:MAIN.O AAA.O BBB.O CCC.O     

We can see that the [. O] File string has been repeated two times, and if our project needs to add a new [. o] File, then we need to add in two places (should be three places and a place in clean). Of course, our makefile is not complicated, so we are not tired in two places, but if Makefile becomes complex, then we may forget a place to join and cause compilation to fail. Therefore, in order to makefile easy maintenance, we can use variables in makefile. The makefile variable is also a string, which can be better understood as a macro in the C language.

For example, we declare any variable name, called OBJECTS, OBJECTS, Objs, Objs, obj, or obj, as long as the obj file can be represented. We define this variable at the beginning of the makefile as follows:

Thus, we can easily use this variable in our makefile in the form of "$ (objects)", so our modified version makefile becomes as follows:

objects =$(objects)    -O-Edit $(objects      ) main.o:main.c-c MAIN.CAAA.O:AAA.C   AAA.h     -c aaa.cbbb.o:bbb.c   BBB.h    -c bbb.cccc.o:ccc.c   CCC.h    -C Ccc.cclean: c16/>

If a new. o file is added, we simply need to modify the variable objects.

3.4 Let make automatically deduce

GNU make is very powerful, it can automatically deduce the file and the command behind the file dependencies, so we don't have to write a similar command after each [. o] File, because our make will automatically recognize and deduce the command ourselves.

As soon as make sees a [. o] File, it automatically adds the [. c] File to the dependency, and if makes finds a whatever.o, then WHATEVER.C is the WHATEVER.O dependent file. And Cc-c Whatever.c will also be deduced, so our makefile no longer need to write so complicated. Our new makefile is in the oven again.

objects ==$(objects)    -O-Edit $(objects) main.o:main.c  aaa.o:aaa.c   AAA.HBBB.O:BBB.C   bbb.hccc.o:ccc.c   ccc.h.phony:cleanclean:    

This method, the "cryptic rule" of make. The contents of the above file, ". Phony "means that clean is a pseudo-target file.

The introduction to the basic can be finished, but there are two more to say

3.5 Alternative style of makefile

Since make can automatically deduce the command, I see that the pile of [. O] and [. h] Dependencies are a bit uncomfortable, so many repetitive [. h], can you put it together, OK, no problem, this is easy for make, to see the latest style of makefile bar.

objects ==$(objects)    -O-Edit $(objects) main.o:main.c  AAA.O: Aaa.hbbb.o:bbb.hccc.o:ccc.h.phony:cleanclean:    rm edit MAIN.O aaa.o bbb.o ccc.o

In fact, this has not explained the problem, I will simply use the language to describe, if AAA.O and bbb.o common head file AAA.h, it can be written as

AAA.O bbb.o:aaa.h

If the files are used BBB.h can be written as:

$ (objects): BBB.h

This style, Makefile becomes very simple, but the file dependency is a bit messy. Look at your preferences. I do not like this style, one is the document dependencies can not see clearly, and second, if more than one file, to add a few new. o files, it is not clear.

3.6 Rules for emptying target files

Each makefile should write a rule that clears the target file (. O and Execute file), which is not only easy to recompile, but also helps keep the file clean. The general style is:

Clean :     $ (objects)

A more robust approach is to:

. Phony:cleanclean:    -rm Edit $ (objects)

As I said before. Phony means that clean is a "pseudo-target". and a small minus sign in front of the RM command means that some files may be in trouble, but leave it behind (assuming you manually delete a file to ensure that other files can be deleted).

Of course, clean rules do not put in the beginning of the file, otherwise, it will become the default goal of make, I believe that no one is willing to do so. The unwritten rule is that "clean is always at the end of the file."

Introduction here, the whole make on the introduction, and a little bit of knowledge, I will copy the blog for your reference

4.make Supplemental ContentWhat's in makefile?

Makefile contains five main things: explicit rules, cryptic rules, variable definitions, file instructions, and annotations.

      1. An explicit rule. Explicit rules describe how to generate one or more target files. This is clearly indicated by the writer of the makefile, to generate the file, the file's dependent file, the generated command.
      2. Obscure rules. Because our make has an automatic derivation function, the obscure rules allow us to write makefile in a relatively brief way, which is supported by made.
      3. The definition of the variable. In makefile we want to define a series of variables, which are usually strings, which is a bit like the macro in your C language, and when Makefile is executed, the variables are extended to the corresponding reference positions.
      4. File instructions. It consists of three parts, one referencing another makefile in one makefile, just like the include in C, and the other is specifying a valid part of makefile based on certain circumstances, just like the precompiled # if in C language And there is a command that defines a multiline. I'll tell you about this part of the story in the next section.
      5. Comments. In makefile, just the line comment, like the Unix shell script, is annotated with the "#" character, which is like the "//" in C/s + +. If you want to use the "#" character in your makefile, you can escape it with a backslash, for example: "\#".

Finally, it is worth mentioning that the command in makefile must start with the [Tab] key.

filename of the makefile

By default, the make command searches the current directory for files named "Gnumakefile", "Makefile", and "makefile" in the order found to interpret the file. In these three file names, it is best to use the "Makefile" file name, because the first character of this file name is uppercase, so there is a sense of purpose. It is best not to use "Gnumakefile", which is the GNU make recognition. There are other make that are only sensitive to the "makefile" file name in full lowercase, but basically, most of them support both the "makefile" and "makefile" default filenames.

Of course, you can use a different file name to write makefile, such as: "Make.linux", "Make.solaris", "Make.aix", etc., if you want to specify a specific makefile, you can use make "-F" and "--file" parameters , such as: Make-f make.linux or make--file Make.aix.

refer to other makefile

Using the Include keyword in makefile can include other makefile, much like the C # # #, where the contained file is placed in the current file's containing location. The syntax for include is:

Include <filename>;

FileName can be the file mode of the current operating system shell (can include path and wildcard characters)

There can be some empty characters in front of the include, but it must never be the [Tab] key to start. Include and <filename>; can be separated by one or more spaces. For example, you have a few makefile:a.mk, B.mk, C.mk, and a file called Foo.make, and a variable $ (bar) that contains e.mk and F.MK, then the following statement:

Include Foo.make *.mk $ (bar)

Equivalent to:

Include Foo.make a.mk b.mk c.mk e.mk f.mk

When the make command starts, it will look for the other makefile indicated by the include and place its contents in its current position. It's like a C + + # include directive. If the file does not specify an absolute path or a relative path, make will look in the current directory first, and if not found in the current directory, make will also be found in the following several directories:

      1. If make executes with the "-I" or "--include-dir" parameter, then make will look in the directory specified in this parameter.
      2. If the directory <prefix>;/include (typically:/usr/local/bin or/usr/include) exists, make will also look for it.

If a file is not found, make generates a warning message, but the fatal error does not occur immediately. It will continue to load other files, and once the makefile has been read, make will retry the files that are not found, or cannot be read, and if not, make will be presented with a fatal message. If you want make to ignore the unreadable files and continue, you can add a minus "-" before the include. Such as:

-include <filename>;

It indicates that no error will continue to occur, regardless of any errors in the include process. The related commands that are compatible with other versions of Make are sinclude, and the effect is the same as this one.

environment variable makefiles

If the environment variable makefiles is defined in your current environment, make makes an action similar to include in the value of this variable. The values in this variable are other makefile, separated by a space. But, unlike include, the makefile "target" introduced from this environment variable will not work, and if the file defined in the environment variable finds an error, make will ignore it.

But here I still recommend not to use this environment variable, because as long as this variable is defined, then when you use make, all the makefile will be affected by it, this is not what you want to see. In this case, just to tell you that there may be times when your makefile appear strange, then you can see if there is any definition of this variable in the current environment.

how make Works

The GNU make works at the following steps: (think of other make also similar)

      1. Read into all the makefile.
      2. Read the other makefile that are included.
      3. Initializes a variable in the file.
      4. Derive the cryptic rules and analyze all the rules.
      5. Create a dependency chain for all the target files.
      6. Depending on the dependencies, decide which targets to regenerate.
      7. Executes the build command.

1-5 steps for the first stage, and 6-7 for the second stage. In the first stage, if the defined variable is used, make will expand it to the location in use. But make does not start all at once, making uses procrastination tactics, and if a variable appears in a dependency rule, the variable will be expanded within it only if the dependency is determined to be used.

Compilation of C-language multi-Files and application of makefile in Linux

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.