1. Static connection and dynamic connection
There are two types of links: static links and dynamic links .
1) Static linking
Static linking: The linker adds the contents of the library to the executable program at link time.
advantage:
- Less dependence on the operating environment and better compatibility
shortcoming:
- The generated program is larger, requires more system resources, and consumes more time when loading into memory.
- The library function has been updated and the application must be recompiled
2) Dynamic link
Dynamic linking: The connector only establishes the link relationship with the required library functions when linking, and transfers the required resources into the executable program when the program is running.
advantage:
- The corresponding resource function will be called when needed.
- Simplifies program upgrades; has smaller program size
- Realize resource sharing between processes (avoid repeated copies)
shortcoming:
- Depends on dynamic library and cannot run independently
- Dynamic library dependency version problem is serious
3) Comparison of static and dynamic compilation
The application program we wrote earlier uses a large number of standard library functions. The system uses dynamic linking by default to compile the program. If you want to use static compilation, add the -static parameter.
The following is a comparison of files when dynamic compilation and static compilation are used:
The test program (test.c) is as follows:
#include <stdio.h>
int main(void)
{
printf("hello world\n");
return 0;
}
Compile:
deng@itcast:~/test$ gcc test.c -o test_share
deng@itcast:~/test$ gcc -static test.c -o test_static
Comparative Results:
2. Introduction to static libraries and dynamic libraries
The so-called "program library", simply put, is a file containing data and execution code. It cannot be executed alone and can be used as part of other execution programs to complete certain functions.
The existence of libraries can modularize programs, speed up program recompilation, enable code reuse, and make programs easy to upgrade.
Program libraries can be divided into static libraries and shared libraries .
3. Production and use of static libraries
A static library can be thought of as a collection of target codes that have been added to the executable code before the executable program is run and become part of the executable program.
According to custom, ".a" is generally used as the file suffix. The naming of static libraries is generally divided into three parts:
- Prefix: lib
- Library name: You can define it yourself
- Suffix: .a
So the final static library name should be: libxxx.a
1) Static library production
Step 1: Generate the c source file into the corresponding .o file
deng@itcast:~/test/3static_lib$ gcc -c add.c -o add.o
deng@itcast:~/test/3static_lib$ gcc -c sub.c -o sub.odeng@itcast:~/test/3static_lib$ gcc -c mul.c -o mul.o
deng@itcast:~/test/3static_lib$ gcc -c div.c -o div.o
Step 2: Use the packaging tool ar to package the prepared .o file into an .a file libtest.a
deng@itcast:~/test/3static_lib
$ ar -rcs libtest.a add.o sub.o mul.o div.o
When using the ar tool, you need to add parameters: rcs
- rUpdate
- cCreate
- s index
2) Static library usage
After the static library is produced, the .a file and header file need to be released to users together.
Assume that the test file is main.c, the static library file is libtest.a, and the header file is head.h.
Compile command:
deng@itcast:~/test/4static_test$ gcc test.c -L./ -I./ -ltest -o test
Parameter Description:
- -L: Indicates the directory where the library to be connected is located
- -I./: I (capital i) indicates that the directory of the specified header file is the current directory
- -l (lowercase L): Specify the library required for linking, remove the prefix and suffix
13. Production and use of dynamic libraries
Shared libraries are not linked into the target code when the program is compiled, but are loaded when the program is run. If different applications call the same library, they only need to have one instance of the shared library in the memory, avoiding the problem of wasted space.
The dynamic library is loaded when the program is running, which also solves the problem that the static library will cause trouble to the update, deployment and release page of the program. Users only need to update the dynamic library, incremental update.
According to custom, ".so" is generally used as the file suffix. The naming of shared libraries is generally divided into three parts:
- Prefix: lib
- Library name: You can define it yourself
- Suffix: .so
So the final dynamic library name should be: libxxx.so
1) Dynamic library production
Step 1: Generate the target file. At this time, add the compilation option: -fPIC (fpic)
deng@itcast:~/test/5share_lib$ gcc -fPIC -c add.c
deng@itcast:~/test/5share_lib$ gcc -fPIC -c sub.c deng@itcast:~/test/5share_lib$ gcc -fPIC -c mul.c deng@itcast:~/test/5share_lib$ gcc -fPIC -c div.c
Parameters: -fPIC creates a position independent code (pic, position independent code) that can be shared among multiple applications.
Step 2: Generate a shared library. At this time, add the linker option: -shared (specify to generate a dynamic link library)
deng@itcast:~/test/5share_lib$ gcc -shared add.o sub.o mul.o div.o -o libtest.so
Step 3: View the corresponding function through nm command
deng@itcast:~/test/5share_lib$ nm libtest.so | grep add 00000000000006b0 T add deng@itcast:~/test/5share_lib$ nm libtest.so | grep sub 00000000000006c4 T sub
ldd checks the dynamic libraries that an executable file depends on
deng@itcast:~/share/3rd/2share_test$ ldd test linux-vdso.so.1 => (0x00007ffcf89d4000) libtest.so => /lib/libtest.so (0x00007f81b5612000) libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6 (0x00007f81b5248000) /lib64/ld-linux-x86-64.so.2 (0x00005562d0cff000)
2) Dynamic library testing
Reference the dynamic library and compile it into an executable file (the same as the static library)
deng@itcast:~/test/6share_test$ gcc test.c -L. -I. -ltest (-I. uppercase i -ltest lowercase L)
Then run: ./a.out and find that an error is reported! ! !
- When the system loads executable code, it can know the names of the libraries it depends on, but it also needs to know the absolute path. At this time, the system dynamic loader (dynamic linker/loader) is needed.
- For elf format executable programs, it is completed by ld-linux.so*, which successively searches the DT_RPATH section of the elf file - environment variable LD_LIBRARY_PATH - /etc/ld.so.cache file list - /lib/, /usr /lib directory finds the library file and loads it into memory.
3) How to let the system find the dynamic library
the first method:
Copy the shared library you made to /lib or /usr/lib (not the /lib64 directory)
cp libxxx.so /url/lib
The second method:
Temporarily set LD_LIBRARY_PATH
export LD_LIBRARY_PATH=$LD_LIBRARY_PATH: library path
Third method:
For permanent settings, set export LD_LIBRARY_PATH=$LD_LIBRARY_PATH: library path to ~/.bashrc or /etc/profile file
deng@itcast:~/share/3rd/2share_test$ vim ~/.bashrc
Add the following to the last line:
export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:/home/deng/share/3rd/2share_test
(Enable environment variables to take effect)
deng@itcast:~/share/3rd/2share_test$ source ~/.bashrc deng@itcast:~/share/3rd/2share_test$ ./test
a + b = 20 a - b = 10
Fourth method:
Add this to the /etc/ld.so.conf file
Edit the /etc/ld.so.conf file and add the path to the directory where the library file is located.
deng@itcast:~/share/3rd/2share_test$ sudo vim /etc/ld.so.conf
Add the dynamic library path (absolute path) at the end of the file
Run sudo ldconfig -v, which will rebuild the /etc/ld.so.cache file
deng@itcast:~/share/3rd/2share_test$ sudo ldconfig
The fifth method:
Use symbolic links, but be sure to use absolute paths
deng@itcast:~/test/6share_test$ sudo ln -s /home/deng/test/6share_test/libtest.so /lib/libtest.so
Summarize:
Static linking compiles all dependent library functions directly into the final executable file, providing high independence and execution efficiency, but may result in large disk and memory usage, and updating library functions requires recompiling. Dynamic linking dynamically loads library functions when the program is running, which effectively saves storage space and facilitates the updating and sharing of library functions. However, it needs to ensure that the correct version of the library is in the appropriate location during runtime, and may affect execution efficiency.