1 Introduction to C

1.2 Compiling and program structure

1.2.1 Quick start

It is well-known that one starts to learn a new programming language by writing a program to print “hello world”. This example was given in K&R with the following C program.

Above program contains the main function, in which a printf function is called to print “hello, world”. Let’s start our hands-on work with this hello world program. Open a text editor say notepad (or notepad++ if it is installed), type in the program, and save it as a text file with a name that ends in “.c”, such as hello.c. Then open a command console, cd to the directory, where hello.c is saved. Type the following command to compile (assuming that the GCC compiler was installed).

gcc hello.c

The compiling will create an executable program named a.exe in the same folder under Windows OS, or a.out in Linux or macOS. Under Windows, we run a.exe by command: a.exe or simply a. Under Linux, we run a.out by command: ./a.out or simply ./a. The output on the console will be:

hello, world

Now you have created, compiled, and run your first C program.

1.2.2 Compiling and execution

Command gcc hello.c -o hello.exe creates the same executable program of file name hello.exe as specified by the output option -o in command line.

What happens with compiling?

The compiling converts a C source code program to an executable program. The compiler does the compiling in order of the following steps:

1. Preprocessing

Resolve lines with preprocessor directives, i.e., lines starting with “#”. For example, the first line of Listing 1 is a preprocessor directive #include <stdio.h>, which brings in (reads or insert) the stdio library header file stdio.h to the program during the preprocessing.

2. Compilation

Convert the C source code program into an assembly program, i.e., a program in assembly language. An assembly program consists of a sequence of readable machine instructions such as read/write data from/to memory to/from CPU registers, add numbers in registers.

3. Assembling

Convert the assembly program to a binary machine program, called object program.

4. Linking

Combine the necessary object programs together to create an executable program of binary machine code program. For example, Listing 1 uses the printf function, which is a library function declared in stdio.h header file. The linking will bring in the machine code program of printf from the C library of object programs to build the final executable hello.exe program.

Compiler options

GCC compilers have options to do compiling. Command gcc --help will list available options for gcc. The following options are commonly used.

Table 1: Compile options
Option Purpose Example
-std=c99 Use C99 standard for compiling Command gcc –std=c99 hello.c will use the C99 compliant compiler to compile.
-c Suppress linking step, just generate an object file gcc –c hello.c will create the object program file hello.o
-g Embed diagnostic information into the object file for debugging gcc –g hellow.c
-o Specify output file name gcc –o hello.exe hello.c creates hello.exe file.
-S Suppress the assemble and linking steps and output the assembly program file. gcc –S hello.c will create assembly program file hello.s
-O? Optimization level: 0 off, 1 default, 2, 3, 6 higher level gcc –O3 hello.c
-Wall Give compiling warning gcc –Wall hello.c

C programming has the following file name extension convention.

Table 2: File extension convention
Extension File type
.c C program source code file, e.g. hello.c
.h C program header file, e.g., sdtio.h
.exe Default executable program file for Windows OS, .out for Linux and macOS.
.o Object file, e.g. hello.o
.s Assembly program source file, e.g., hello.s
.lib Static library of object modules (.a for UNIX/Linux/macOS)
.dll Dynamic library file for Windows OS (.so for UNIX/Linux/macOS)

What happens when running an executable program?

When issuing command hello.exe in the command console, the console starts a new process which loads the executable program hello.exe into the main memory, and starts the execution of the program from the first instruction of the main function.

At execution, an instruction is read from memory to CPU. CPU does the operation according to the instruction. After the instruction execution is complete, program flow control gets the next instruction, which can be the instruction after the previous one, or an instruction in another location.

The execution terminates at the end of the main function. The process of running the program exits and the console returns the prompt for next command input.

1.2.3 C program structures

To build an executable program, a main function must be presented in the source code program file. That defines the starting point of the program. The main function contains a sequence of statements. A statement may contain a function call, i.e., calling to run another function.

Generally, a function contains a sequence of statements, and a function can call other functions including itself. Statements (sometimes called commands) are executed strictly one after the other. In computer science, such kind of programming is called imperative programming and further organizing statements into functions is called procedural programming.

The function based program construction defines the C program structure. A C program is organized as a collection of functions, one of them is the main function. A function contains a sequence of statements. A statement may call another function. Functions are related by calling relations.

Function A is dependent on function B, if function B is called in function A, and function B must be presented (declared or defined) when function A calls it. Otherwise the compiler will be confused by the function name. Thus the appearances of functions in source code program must be in right ordering . This adds difficulties in managing C functions. To avoid the issues caused by the function ordering, a common practice in C programming is to declare all functions before they are defined and used. In this way, the ordering of function definitions/implementations does not matter any more. The following is a general model of C program structures.

[preprocessor directives]
[global variables]
[function declarations]
main( arguments ) {
  [statements]
}
[function definitions]

Here, we use [] to represent a list of items. The following C program example uses the above C program structure model.

In the main function, statement printf("a+b=%d\n",add(a,b)); calls the stdio library format print function printf. The printing format is specified by format argument “a+b=%d”, where %d will be replaced by the integer string of the return value of function call add(a, b). Save the above program file file, say testmain.c, compile and run the program in command line console:

gcc testmain.c -o testmain.exe
testmain.exe

We have output:

a+b=3
a-b=-1

1.2.4 C program organization

A C program gets big and complex when the number of functions increases. To manage the complexity of a C program, a C program is often decomposed into several files including function header program files, i.e. files with .h extension, and function implementation program files, i.e. files .c extension). A function implementation program includes a group of function header files if the its functions call the functions given in the header files. A function implementation program can be compiled separately into object programs by using the -c option. A function implementation program may not contain the main function. The set of object programs (one of them must contain the main function) can be linked together to create an executable program.

The following code lists show an example of decomposing the above program into three files.

test.h

The following command compile all necessary programs to create the executable program.

gcc addsub.c addsub_main.c -o testmain.exe

The following commands show the partial comiling and linking to create the executable program.

gcc addsub.c -c
gcc addsub_main.c -c
gcc addsub.o addsub_main.o -o testmain.exe

The first two commmands create object programs addsub.o and addsub_main.o respectively. The last command links the two object programs to create the executable program testmain.exe

1.2.5 Exercises

Self-quiz

Take a moment to review what you have read above. When you feel ready, take this self-quiz which does not count towards your grade but will help you to gauge your learning. Answer the questions posed below.

Go back