📄 c-on-unix.html
字号:
<hr size=4><a name="compiler_warnings"><font color=brown><h2>Getting Extra Compiler Warnings</h2></font></a><p>Normally the compiler only generates error messages about erroneous codethat does not comply with the C standard, and warnings about things thatusually tend to cause errors during runtime. However, we can usually instructthe compiler to give us even more warnings, which is useful to improve thequality of our source code, and to expose bugs that will really bug us later.With gcc, this is done using the '-W' flag. For example, to get the compilerto use all types of warnings it is familiar with, we'll use a command linelike this:<br><br><code>cc -Wall single_source.c -o single_source</code><br><br>This will first annoy us - we'll get all sorts of warnings that mightseem irrelevant. However, it is better to eliminate the warnings thanto eliminate the usage of this flag. Usually, this option will save usmore time than it will cause us to waste, and if used consistently, we will get used to coding proper code without thinking too much about it. One shouldalso note that some code that works on some architecture with one compiler,might break if we use a different compiler, or a different system, to compilethe code on. When developing on the first system, we'll never see these bugs,but when moving the code to a different platform, the bug will suddenly appear.Also, in many cases we eventually will want to move the code to a newsystem, even if we had no such intentions initially.</p><p>Note that sometimes '-Wall' will give you too many errors, and then youcould try to use some less verbose warning level. Read the compiler's manualto learn about the various '-W' options, and use those that would give youthe greatest benefit. Initially they might sound too strange to make any sense,but if you are (or when you will become) a more experienced programmer, youwill learn which could be of good use to you.</p><hr size=4><a name="single_source_cpp"><font color=brown><h2>Compiling A Single-Source "C++" Program</h2></font></a><p>Now that we saw how to compile C programs, the transition to C++ programs israther simple. All we need to do is use a C++ compiler, in place of the C compiler we used so far. So, if our program source is in a file named <A href="single_main.cc">'single_main.cc'</a> ('cc' to denote C++ code.Some programmers prefer a suffixof 'C' for C++ code), we will use a command such as the following:<br><br><code>g++ single_main.cc -o single_main</code><br><br>Or on some systems you'll use "CC" instead of "g++" (for example, withSun's compiler for Solaris), or "aCC" (HP's compiler), and so on. You wouldnote that with C++ compilers there is less uniformity regarding commandline options, partially because until recently the language was evolving andhad no agreed standard. But still, at least with g++, you will use "-g" fordebug information in the code, and "-O" for optimization.</p><hr size=4><a name="multi_source_c"><font color=brown><h2>Compiling A Multi-Source "C" Program</h2></font></a><p>So you learned how to compile a single-source program properly (hopefullyby now you played a little with the compiler and tried out a few examplesof your own). Yet, sooner or later you'll see that having all the source ina single file is rather limiting, for several reasons:<ul><li> As the file grows, compilation time tends to grow, and for each little change, the whole program has to be re-compiled.<li> It is very hard, if not impossible, that several people will work on the same project together in this manner.<li> Managing your code becomes harder. Backing out erroneous changes becomes nearly impossible.</ul>The solution to this would be to split the source code into multiple files,each containing a set of closely-related functions (or, in C++, all the sourcecode for a single class).</p><p>There are two possible ways to compile a multi-source C program. The firstis to use a single command line to compile all the files. Suppose that wehave a program whose source is found in files<a href="multi-source/main.c">"main.c"</a>,<a href="multi-source/a.c">"a.c"</a> and<a href="multi-source/b.c">"b.c"</a>(found in directory <a href="multi-source/">"multi-source"</a> of this tutorial).We could compile it this way:<br><br><code>cc main.c a.c b.c -o hello_world</code><br><br>This will cause the compiler to compile each of the given files separately, andthen link them all together to one executable file named "hello_world". Twocomments about this program:<ol><li> If we define a function (or a variable) in one file, and try to access them from a second file, we need to declare them as external symbols in that second file. This is done using the C <code>"extern"</code> keyword.<li> The order of presenting the source files on the command line may be altered. The compiler (actually, the linker) will know how to take the relevant code from each file into the final program, even if the first source file tries to use a function defined in the second or third source file.</ol>The problem with this way of compilation is that even if we only make a changein one of the source files, all of them will be re-compiled when we runthe compiler again.</p><p>In order to overcome this limitation, we could divide the compilation processinto two phases - compiling, and linking. Lets first see how this is done,and then explain:<br><pre><code>cc -c main.cccc -c a.ccc -c b.ccc main.o a.o b.o -o hello_world</code></pre><br>The first 3 commands have each taken one source file, and compiled it intosomething called "object file", with the same names, but with a ".o" suffix.It is the "-c" flag that tells the compiler only to create an objectfile, and not to generate a final executable file just yet.The object file contains the code for the source file in machine language,but with some unresolved symbols. For example, the "main.o" file refersto a symbol named "func_a", which is a function defined in file "a.c". Surelywe cannot run the code like that. Thus, after creating the 3 object files,we use the 4th command to link the 3 object files into one program. The linker(which is invoked by the compiler now) takes all the symbols from the 3 objectfiles, and links them together - it makes sure that when "func_a" is invokedfrom the code in object file "main.o", the function code in object file "a.o"gets executed. Further more, the linker also links the standard C libraryinto the program, in this case, to resolve the "printf" symbol properly.</p><p>To see why this complexity actually helps us, we should note that normallythe link phase is much faster than the compilation phase. This is especiallytrue when doing optimizations, since that step is done before linking. Now,lets assume we change the source file "a.c", and we want to re-compile theprogram. We'll only need now two commands:<br><br><pre><code>cc -c a.ccc main.o a.o b.o -o hello_world</code></pre><br><br>In our small example, it's hard to notice the speed-up, but in a case ofhaving few tens of files each containing a few hundred lines of source-code,the time saving is significant; not to mention even larger projects.</p><hr size=4><a name="compilation_steps"><font color=brown><h2>Getting a Deeper Understanding - Compilation Steps</h2></font></a><p>Now that we've learned that compilation is not just a simple process, lets tryto see what is the complete list of steps taken by the compiler in orderto compile a C program.<ol><li> <code><u>Driver</u></code> - what we invoked as "cc". This is actually the "engine", that drives the whole set of tools the compiler is made of. We invoke it, and it begins to invoke the other tools one by one, passing the output of each tool as an input to the next tool.<li> <code><u>C Pre-Processor</u></code> - normally called "cpp". It takes a C source file, and handles all the pre-processor definitions (#include files, #define macros, conditional source code inclusion with #ifdef, etc.) You can invoke it separately on your program, usually with a command like: <br><br> cc -E single_source.c <br><br> Try this and see what the resulting code looks like.<li> <code><u>The C Compiler</u></code> - normally called "cc1". This is the actual compiler, that translates the input file into assembly language. As you saw, we used the "-c" flag to invoke it, along with the C Pre-Processor, (and possibly the optimizer too, read on), and the assembler.<li> <code><u>Optimizer</u></code> - sometimes comes as a separate module and sometimes as the found inside the compiler module. This one handles the optimization on a representation of the code that is language-neutral. This way, you can use the same optimizer for compilers of different programming languages.<li> <code><u>Assembler</u></code> - sometimes called "as". This takes the assembly code generated by the compiler, and translates it into machine language code kept in object files. With gcc, you could tell the driver to generated only the assembly code, by a command like: <br><br> <code> cc -S single_source.c </code> <br><br><li> <code><u>Linker-Loader</u></code> - This is the tool that takes all the object files (and C libraries), and links them together, to form one executable file, in a format the operating system supports. A Common format these days is known as "ELF". On SunOs systems, and other older systems, a format named "a.out" was used. This format defines the internal structure of the executable file - location of data segment, location of source code segment, location of debug information and so on.</ol></p><p>As you see, the compilation is split in to many different phases. Not allcompiler employs exactly the same phases, and sometimes (e.g. for C++compilers) the situation is even more complex. But the basic idea isquite similar - split the compiler into many different parts, to give the programmer more flexibility, and to allow the compiler developersto re-use as many modules as possible in different compilers for differentlanguages (by replacing the preprocessor and compiler modules), or fordifferent architectures (by replacing the assembly and linker-loader parts).</p><hr size=4><p align=center><img src=http://www.actcom.co.il/~choo/lupg/images/lupg_toolbar.gif height=40 width=360 alt="" usemap="#lupg_map"><map name=lupg_map><area shape=rect coords="3,0 37,39" href=http://www.actcom.co.il/~choo/lupg alt="LUPG home"><area shape=rect coords="67,0 102,39" href=http://www.actcom.co.il/~choo/lupg/tutorials/index.html alt="Tutorials"><area shape=rect coords="138,0 170,39" href=http://www.actcom.co.il/~choo/lupg/related-material.html alt="Related material"><area shape=rect coords="213,0 232,39" href=http://www.actcom.co.il/~choo/lupg/project-ideas/index.html alt="Project Ideas"><area shape=rect coords="272,0 290,39" href=http://www.actcom.co.il/~choo/lupg/essays/index.html alt="Essays"><area shape=rect coords="324,0 355,39" href=mailto:choo@actcom.co.il alt="Send comments"></map><br>[<a href=http://www.actcom.co.il/~choo/lupg/index.html>LUPG Home</a>] [<a href=http://www.actcom.co.il/~choo/lupg/tutorials/index.html>Tutorials</a>] [<a href=http://www.actcom.co.il/~choo/lupg/related-material.html>Related Material</a>] [<a href=http://www.actcom.co.il/~choo/lupg/essays/index.html>Essays</a>] [<a href=http://www.actcom.co.il/~choo/lupg/project-ideas/index.html>Project Ideas</a>] [<a href=mailto:choo@actcom.co.il>Send Comments</a>]<br><img src=http://www.actcom.co.il/~choo/lupg/images/good_bar.gif alt=""></p> <p>This document is copyright (c) 1998-2002 by guy keren.<br><br>The material in this document is provided AS IS, without anyexpressed or implied warranty, or claim of fitness for aparticular purpose. Neither the author nor any contributers shellbe liable for any damages incured directly or indirectly by usingthe material contained in this document.<br><br>permission to copy this document (electronically or on paper, forpersonal or organization internal use) or publish it on-line ishereby granted, provided that the document is copied as-is, thiscopyright notice is preserved, and a link to the original documentis written in the document's body, or in the page linking to thecopy of this document.<br><br>Permission to make translations of this document is also granted,under these terms - assuming the translation preserves the meaningof the text, the copyright notice is preserved as-is, and a linkto the original document is written in the document's body, or inthe page linking to the copy of this document.<br><br>For any questions about the document and its license, please<a href=mailto:choo@actcom.co.il>contact the author</a>.</p> </body></html>
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -