Detailed explanation of Linux dynamic library generation and use guide

  • 2021-08-17 01:43:49
  • OfStack

The file name of dynamic library file under Linux is like libxxx. so, where so is the abbreviation of Shared and Object, that is, the target file that can be shared.

When a dynamic library is linked to generate an executable, the code for the dynamic library is not copied to the execution file, but a reference to the dynamic library is recorded in the execution file.

When the program executes, load the dynamic library file again. If the dynamic library is already loaded, it does not have to be loaded repeatedly, thus saving memory space.

The steps to build and use dynamic libraries under Linux are as follows:

Write source files. Compile and link one or several source files to generate a shared library. Through-L < path > -The gcc option for lxxx links the generated libxxx. so. To run a program linked to libxxx. so, place libxxx. so in the standard path of the link library, or specify LD_LIBRARY_PATH.

The following is a detailed explanation through examples.

Write source files

Create a source file: max. c with the following code:


int max(int n1, int n2, int n3)
{
  int max_num = n1;
  max_num = max_num < n2? n2: max_num;
  max_num = max_num < n3? n3: max_num;
  return max_num;
}

Compile and build shared libraries:


gcc -fPIC -shared -o libmax.so max.c

We'll get libmax. so.

In fact, the above process is divided into two steps: compilation and linking.-fPIC is the compilation option, and PIC is the abbreviation of Position Independent Code, which means that location-independent code should be generated, which is a feature required by dynamic library; -shared is a link option that tells gcc to generate dynamic libraries instead of executable files.

The above 1-line command is equivalent to:


gcc -c -fPIC max.c
gcc -shared -o libmax.so max.o

Writing Interface Files for Dynamic Libraries

In order to let users know which interfaces are available in our dynamic library, we need to write corresponding header files.

To establish max. h, enter the following code:


#ifndef __MAX_H__
#define __MAX_H__

int max(int n1, int n2, int n3);

#endif

Test, link dynamic library to generate executable file

Create an test. c using the max function with the following code:


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

int main(int argc, char *argv[])
{
  int a = 10, b = -2, c = 100;
  printf("max among 10, -2 and 100 is %d.\n", max(a, b, c));
  return 0;
}

gcc test. c-L.-lmax generates a. out, where-lmax means to link libmax. so.

-L. Indicates that the current path is included when searching for the library file to be linked.

Note that if there are both dynamic and static libraries with the same name in the same directory, for example, libmax. so and libmax. a are both in the current path,
gcc gives priority to linking dynamic libraries.

Run

Running./a. out will get the following error prompt.

./a.out: error while loading shared libraries: libmax.so: cannot open shared object file: No such file or directory

Unable to find libmax. so, originally Linux searched for the dynamic library to link through the file /etc/ld. so. cache.
Wherea/etc/ld. so. cache is generated by the ldconfig program reading the/etc/ld. so. conf file.
(Note that the/lib and/usr/lib is not necessarily included in the/etc/ld. so. conf, which is automatically searched by the ldconfig program.)

If we add the path of libmax. so to the/etc/ld. so. conf, then run the ldconfig program with root privileges, update the/etc/ld. so. cache, and find libmax. so when a. out runs.

But as a simple test example, it doesn't seem appropriate for us to change the system.

Another simple way is to specify LD_LIBRARY_PATH for a. out.


LD_LIBRARY_PATH=. ./a.out

The program will run normally. LD_LIBRARY_PATH=. is a dynamic library that tells a. out to first look for links in the current path.

For the executable program of elf format, it is completed by ld-linux.so*. It searches the DT_RPATH section of elf file, the environment variable LD_LIBRARY_PATH,/etc/ld. so. cache file list,/lib/,/usr/lib directory, and loads it into memory after finding the library file.

makefile Automates Work

Write makefile as follows:


.PHONY: build test clean

build: libmax.so

libmax.so: max.o
 gcc -o $@ -shared $<

max.o: max.c
 gcc -c -fPIC $<

test: a.out

a.out: test.c libmax.so
 gcc test.c -L. -lmax
 LD_LIBRARY_PATH=. ./a.out

clean:
 rm -f *.o *.so a.out

make build generates libmax. so, make test generates a. out and executes, and make clean cleans up compilation and test results.


Related articles: