Het Linking Proces Belicht – Statische vs Dynamische Bibliotheken

okt 19, 2021
admin

Een Statische en Dynamische Bibliotheek Maken

Voor een statische bibliotheek wordt de objectcode van binaire bestanden (extensie .o) gecombineerd in een enkel archiefbestand met extensie .a. Dit archief is vergelijkbaar met een gereedschapskist die alle gereedschappen bevat die kunnen worden gebruikt in programma’s die deze bibliotheek tijdens het linken aanroepen. De tools worden ingevoegd op plaatsen waar ze nodig zijn. In de afbeelding hieronder heb ik een serie .c bestanden.

Omdat een bibliotheek een archief van object code is, moet ik al deze .c bestanden omzetten in .o bestanden met het volgende commando:

gcc -Wall -Wextra -Werror -pedantic -c *.c

De -c optie stopt het compilatie proces vlak voor het linken nadat de object code bestanden zijn gegenereerd. Ik heb nu alle object code bestanden:

Als ik het commando ar -rc libholbertonschool.a *.o uitvoer, kan ik deze bestanden archiveren in een enkel .a bibliotheek bestand. Het ar commando is voor het archiveren, de -r optie is voor het verplaatsen van leden die extensie .o hebben, en de -c optie is voor het maken van het archief als het niet bestaat. Een bibliotheekbestand begint met een voorvoegsel lib en heeft een extensie .a. De laatste stap die op sommige systemen nodig is, is het indexeren van de inhoud van het archief om het linken te versnellen. Dit kan worden gedaan met ranlib libholbertonschool.a. Ik heb nu een bibliotheek die object code bevat voor alle functies in de bovenstaande afbeelding.

De statische bibliotheek gebruiken

Om deze bibliotheek te gebruiken met een of ander testbestand, moet ik het testbestand compileren met de bibliotheek met een van de volgende twee commando’s:

gcc test.c ./libholbertonschool.a -o exename

gcc test.c -L. -lholbertonschool -o exename

Beide doen hetzelfde, maar de tweede is iets meer cryptisch. De -L. optie zoekt naar bibliotheken in de huidige directory en de -l die verbonden is met holbertonschool zoekt impliciet naar het bibliotheekbestand waarbij een lib prefix en .a suffix worden verondersteld. Zonder te compileren met een bibliotheekbestand, zal gcc een fout geven omdat de functies die het probeert te linken niet worden geleverd. Door een bibliotheek in de compilatie mee te leveren, kan de compiler nu de bibliotheek doorzoeken voor de functies die het nodig heeft en ze invoegen waar ze nodig zijn.

Dynamische bibliotheken

Het maken van dynamische bibliotheken is iets anders dan statische bibliotheken, maar de concepten zijn over het algemeen hetzelfde. Ik heb hetzelfde aantal .c bestanden en het header bestand dat hun prototypes definieert in een bestand genaamd lists.h.

Om de dynamische bibliotheek te maken, die een .so (staat voor gedeeld object) heeft, kan het volgende compilatie commando worden ingevoerd:

gcc -fPIC -Wall -Werror -Wextra -pedantic *.c -shared -o libholberton.so

De -fPIC vlag staat voor Positie Onafhankelijke Code die nodig is voor dynamisch linken. De betekenis hiervan is precies wat het klinkt – aangezien dynamisch gelinkte bibliotheken overal in het geheugen kunnen worden opgeslagen waar ze passen, staat deze vlag toe dat het bibliotheekbestand wordt gebruikt ongeacht waar het is opgeslagen.

De vlag -shared staat toe dat een gedeeld archief wordt gemaakt en de optie -o staat ons toe om het uitvoerbestand te hernoemen naar libholberton.so.

Na het uitvoeren van dit commando, heb ik nu een gedeelde bibliotheek!

Gebruik van de dynamische bibliotheek

Stel dat ik de volgende code heb:

#include "holberton.h"
#include <stdlib.h>
#include <stdio.h>/**
* main - check the code for Holberton School students.
*
* Return: Always EXIT_SUCCESS.
*/
int main(void)
{
printf("%d\n", _strlen("Holberton"));
return (EXIT_SUCCESS);
}

Ik kan het programma compileren met de volgende code:

gcc -Wall -pedantic -Werror -Wextra -L. 0-main.c -lholberton -o len 

Net als bij de statische bibliotheken wordt met de -L. opties in de directory gezocht naar bibliotheekbestanden en de -l die aan het begin van holberton wordt toegevoegd is een impliciete zoekactie naar bibliotheekbestanden die een voorvoegsel lib, een achtervoegsel .so, en holberton tussen de twee hebben.

Om het bibliotheekbestand te gebruiken dat ik zojuist heb gemaakt, moet ik ervoor zorgen dat de compiler in staat is om alle bibliotheekbestanden in het geheugen te vinden en dat ze goed in het geheugen zijn geladen om mee te beginnen. Als ik nu ldd len uitvoer, zie ik het volgende:

De regel libholberton.so => not found vertelt me dat de afhankelijkheid van de dynamische bibliotheek die ik zojuist heb gemaakt niet is vervuld. Om dit op te lossen, moet de omgevingsvariabele $LD_LIBRARY_PATH begrepen worden. In Linux is deze variabele een door dubbele punten gescheiden lijst van mappen waarin het systeem op zoek gaat naar bibliotheekbestanden. In de bovenstaande afbeelding kunt u zien dat het echoën van deze variabele in de huidige toestand laat zien dat hij leeg is en dus werkt mijn poging om het programma uit te voeren (len) niet omdat de gedeelde bibliotheek niet kan worden geladen.

Mijn huidige directory ziet er als volgt uit:

Zoals u kunt zien, bevindt het bibliotheekbestand zich in dezelfde directory als mijn hoofdbestand en header-bestand (huidige werkdirectory). Let op de volgende afbeelding:

De opdracht export LD_LIBRARY_PATH=.:$LD_LIBRARY_PATH werkt de omgevingsvariabele $LD_LIBRARY_PATH bij met een .: die aangeeft dat het systeem in de huidige werkdirectory moet zoeken naar bibliotheken. De opdracht export maakt deze wijziging globaal, zodat elke shell dezelfde waarde kan benaderen. Dus, als ik de variabele echo, zie ik mijn updates. Als ik ldd len opnieuw uitvoer, zie ik dat libholberton.so op adreslocatie 0x00007fb9216b9000 staat, wat waarschijnlijk de locatie in de huidige werkdirectory in het geheugen is. Dus, de afhankelijkheid van de executable van de gedeelde bibliotheek is nu vervuld en het programma retourneert 9 wat de lengte is van het woord “Holberton“.

Geef een antwoord

Het e-mailadres wordt niet gepubliceerd.