This method works for both C++ and C.
Say you want to use the function hello
defined in the file hello.cpp
, and you want to use it via a library.
//file hello.cpp
#include <iostream>
void hello(void) {
std::cout<<"hi"<<std::endl;
}
First of all you need to create another file hello.h
and declare the functions (and variables, if any), for hello.cpp
. In C and C++ definition is different from declaration. The rule is define once and declare as many times as you want, and declaration shall precede usage.
//file hello.h
#ifndef HELLO // C macro guard to prevent this file being included more than once
#define HELLO // you can ignore them
void hello(void);
#endif // end of guard
Here is main.cpp
//file main.cpp
#include "hello.h"
int main () {
hello();
return 0;
}
So this is your file structure:
src
|- main.cpp
|- hello.cpp
|- hello.h
Now there are two options, building and linking with static library and dynamic library.
Option 1: Static library
g++ hello.cpp -c -o hello.o // compile to object file
g++ main.cpp -c -o main.o // compile main.cpp to object file
g++ main.o hello.o -o a.out // linked object file and produce executable
Now you may execute the executable a.out
.
Dynamic(Shared) Library
Dynamic library ends in so
. The convention is to name it as libCUSTOMNAME.so
. When linking, pass the flag -lCUSTOMNAME
instead of the file name.
g++ -fPIC hello.cpp -o hello.o // -fPIC produces position independent code.
g++ -shared -Wl,-soname,libhello.so hello.o -o libhello.so // produce the dynamic library file
g++ main.cpp -L$(pwd) -lhello -Wl,-rpath=$(pwd) // compile and link main file
In the last line of the code, $(pwd)
is shell code substitution for path of current directory. -L
specifies the location of the dynamic library file, -Wl,rpath=
specifies run time path.
Remarks
As you can see, building C and C++ source code is troublesome, as you have to manually compile and linking all the libraries. This job is turning even more compilicated for large projects. For quick reference, the Linux Kernel has over 10000 lines of makefile and a custom build system, Kbuild, for building kernel source code. Other project, such as chromium and firefox, are similar.
Many tools are developed to solve this problem, such as gnu make, cmake, gmake, ninga, meson, etc. But in some opinions these tools are not very helpful, as they tries to solve a complicated problem by introducing more complications and idiosyncrasies.