C Libraries

At the bottom of the emulate.h file, you will find the following two lines:

extern machine* initialise(void);
extern void emulate(int, machine *);

These look a little like function definitions, and indeed they do declare functions called initialise and emulate respectively. However, they don't look very much like functions at all, apart from this.

In fact, these lines declare that somewhere else (hence the keyword extern, which means externally to this file) we do in fact have functions called initialise and emulate.

Actually, you'll notice that nothing in this file emulate.h does anything. It's all form and no substance. That is because it is a header file, not a source file as such. The implementation of all these things, in particular the functions initialise and emulate, and the assembly language functions themselves, are all given elsewhere (in this case, in the file called emulate.c).

This combination of a header file (with a .h extension) and an implementation file (with a .c extension) is called a library.

You are already used to including standard C libraries in your programs, but this is an example of a user defined library.

What we are doing, is separating all the code that implements a machine emulator, into a separate C file (emulate.c in this case) so that it can be used by any program, just like a standard C library. The emulate.h header file, tells the main program which loads this library, exactly what it can expect to find in this library, i.e. all the data structures that it has access to, and all the functions it can call.

If you look in the file main.c, which is the main program, you will find the lines:

#include <stdio.h>
#include "emulate.h"

The first of these lines loads up the standard C library stdio (hence the angled brackets), whilst the second line loads up the user defined library (hence the inverted commas), emulate.

Now if you look inside the implementation file emulate.c, you'll find that it includes all the standard C libraries that it uses, and then it has the line:

#include "emulate.h"

In other words, it includes its own header file. This is simply because there are things defined in the header file, which the implementation needs to refer to, e.g. the enum and machine types that we defined and spoke about before. It is very common for implementation files for libraries to include their own header files, and you should make it standard practice to do precisely this in your code.

Note that when you go to compile this program, a number of different files are created. An object (.obj) file is created for both the emulate library, and also for the main program. Finally the linker is called, and it links the two object files together to make them into a single executable program to execute. It is not unusual for large programming projects to have a myriad of libraries invoked by a main program, and to even have libraries include other libraries. For each such library, a different object file is created by the compiler, and they are all linked together at the end by the linker.