Linux Dlopen sistema C

Linux Dlopen Sistema C



Bibliotekos funkcija dlopen() yra labai naudinga funkcija C kalboje. Funkcija įkelia biblioteką į atmintį atidarius naują. Paprastai jį naudojame bibliotekos simboliams, kurie kompiliavimo metu nežinomi, įkelti. Dlopen() yra funkcija, naudojama mūsų programose. DL biblioteka įgyvendina dlopen(), apibrėžtą Dlfcn.h. Dlopen funkcijai reikalingi du parametrai: bibliotekos failo pavadinimas ir vėliavėlė. Failo pavadinimas yra dinaminė biblioteka ir jis apibrėžia, ar bibliotekos priklausomybės apskaičiuojamos iš karto, ar ne. Dlopen() grąžina 'rankeną', kuri turėtų būti laikoma nepermatoma verte, o kitos DL bibliotekos operacijos tai naudoja. Jei bandymas įkelti nesėkmingas, dlopen() grąžina NULL. Tačiau dlopen() grąžina tą pačią failo rankenėlę, jei daug kartų įkelia tą pačią biblioteką.

Naudodamas dlopen funkciją, kompiliatorius netiria galimų klaidų, nes nežino, kokius tipus ir prototipus naudojame. Atrodo, kad jis neskatina dlopen funkcijos diegimo standartiniam įkėlimui, išskyrus keletą nedidelių situacijų. Beje, tai būdas pagerinti savistabą. Kai bendrinamą modulį šiuo metu naudoja kita programa, atminties išdėstymo optimizavimas nėra ypač suinteresuotas sąlyginiu įkėlimu. Atminties plotas nepadidėja, kai įkeliama anksčiau naudota biblioteka. Vengti kompiliatoriaus stebėjimo yra pavojinga ir todėl galima gerai rašyti klaidas. Be to, mums trūksta galimo kompiliatoriaus optimizavimo.

1 pavyzdys:

Dabar apsvarstykite šį pavyzdį, kad pamatytumėte dlopen funkcijos funkcionalumą C kalba. Pirmiausia įkeliame keletą C standartinių bibliotekų. Čia įkeliame naują biblioteką „dlfcn.h“, kuri naudojama makrokomandoms apibrėžti kuriant dlopen režimo argumentą.







Tada savo programoje „gnu/lib-name.h“ pristatome kitą biblioteką. Bendrinamos bibliotekos failus, įtrauktus į GNU libc, randa vartotojo programos pagal jos apibrėžtas makrokomandas. GNU C biblioteka siūlo pagrindines bibliotekas GNU ir GNU/Linux operacinėms sistemoms, taip pat platų kitų Linux pagrindu veikiančių sistemų asortimentą. Po to turime pagrindinį metodo įgyvendinimą. Jo viduje žymeklio objektą paskelbiame „rankena“ naudodami negaliojantį raktinį žodį. Mes deklaruojame rodyklės sinuso funkciją, kurios duomenų tipas yra dvigubas. Yra dar viena žymeklio objekto „klaida“ deklaracija, skirta klaidų tvarkymui.



Po to mes iškviečiame dlopen funkciją „rankenos“ objekto viduje. Dlopen turi du argumentus: LIBM_SO ir „RTLD_LAZY“. Čia „LIBM_SO“ yra bibliotekos failo, kuriame pateikiamos matematinės funkcijos, pvz., trigonometrinės funkcijos, pavadinimas. Ši bendrinama biblioteka reikalinga, nes naudojame sinuso funkciją. „RTLD_LAZY“ yra dar vienas argumentas, kuris iškviečia dlopen funkciją. Kai nurodytas simbolis nurodomas pirmą kartą, perkėlimai turi būti atliekami įgyvendinimo metu nustatytu laiku.



Kadangi procesas negali nurodyti kiekvieno simbolio vykdomajame objekto faile, nurodant RTLD LAZY turėtų padidėti diegimų, įgalinančių dinaminį simbolių susiejimą, našumas. Be to, turime sąlygą if-else, skirtą klaidų apdorojimui, kai rankenos objektas neatlieka dlopen funkcijos. Iškviečiame dlerror, kad pašalintume klaidą.





Funkcija dlerror() pateikia nulinę eilutę, kurią gali perskaityti žmogus, ir nurodo pranešimą apie naujausią klaidą, kurią sukėlė iškvietimas į vieną iš dlopen API iškvietimų po paskutinio dlerror iškvietimo. Tada mes perduodame funkciją taip: „(*void**)(&sine)= dlsym(handle, sin)“. Kadangi tai keista, liejimas atitinka ISO C, todėl išvengiama kompiliatoriaus įspėjimų. Mes naudojame funkciją dlsym, kuri gauna simbolio kelią, kuris yra nurodytas dinaminio ryšio modulyje, kuris pasiekiamas naudojant dlopen () funkciją.

Be to, dar kartą atliekame operaciją if-else standartinei klaidai, kuri sugeneruojama, kai dlerror() nėra NULL. Tada turime printf teiginį, kuriame nurodome sinusinę reikšmę, kurią reikia apskaičiuoti. Paskutiniame veiksme uždarome tą bendrinamą objektą iškviesdami dlclose rankenai, kurią grąžino dlopen ().



#include
#include
#include
#include

tarpt
pagrindinis ( tarpt argc , char ** argv )
{
tuštuma * rankena ;
dvigubai ( * ) ( dvigubai ) ;
char * klaida ;

rankena = dlopen ( LIBM_SO , RTLD_LAZY ) ;
jeigu ( ! rankena ) {
fprintf ( stderr , '%s \n , dlerror ( ) ) ;
išeiti ( EXIT_FAILURE ) ;
}
dlerror ( ) ;

* ( tuštuma ** ) ( & ) = dlsym ( rankena , 'be' ) ;

jeigu ( ( klaida = dlerror ( ) ) != NULL ) {
fprintf ( stderr , '%s \n , klaida ) ;
išeiti ( EXIT_FAILURE ) ;
}

printf ( „%f \n , ( * ) ( 4.0 ) ) ;
dlclose ( rankena ) ;
išeiti ( EXIT_SUCCESS ) ;
}

Mes naudojame parinktį -ldl su C kompiliavimo komanda, nes tai yra dlopen susietos sąsajos biblioteka ir ji yra būtina. Kai vykdomas dlopen failas, jis rodo anksčiau pateiktos reikšmės sinusinę reikšmę.

2 pavyzdys:

Dabar paimame kitą dlopen funkcijos naudojimo pavyzdį. Į savo programą įkeliame visas reikalingas C bibliotekas dlopen kodui įgyvendinti. Tada mes pradedame savo programą pagrindinio metodo viduje. Čia mes apibrėžiame eilutę su kintamojo „src“ deklaracija. Tada paskelbiame rodyklės kintamuosius „strlen“, „handle“ ir „error“.

Tada iškviečiame rankenos kintamąjį ir įdiegiame dlopen funkciją. Funkcija dlopen įveda bendrinamą biblioteką „libstr.so“, skirtą eilučių tvarkymo funkcijoms, ir vėliavėlę „RTLD_LAZY“, kuri jau buvo parodyta ankstesniame pavyzdyje. Mes iškviečiame funkciją dlerror kintamajame „error“, kad pašalintume dlopen funkcijos sugeneruotą klaidą. Jei-kitas naudojamas klaidoms ištirti.

Tada mes gauname strlen funkcijos adresą naudodami funkciją dlsym ir tai darydami patikriname klaidas. Po to mes naudojame funkciją printf, kad iškviestume funkciją strnlen, kad grąžintume nurodytos eilutės ilgį. Galų gale uždarome bendrinamą biblioteką naudodami funkciją dlclose.

#include
#include
#include
#include
tarpt pagrindinis ( tuštuma )
{
char * src = 'Sveiki, Linux' ;
tarpt ( * strlen ) ( konst char * ) ;
tuštuma * rankena ;
char * klaida ;


rankena = dlopen ( './libstr.so' , RTLD_LAZY ) ;
klaida = dlerror ( ) ;
jeigu ( ! rankena || klaida != NULL ) { printf ( „Bendrinimas įkelti biblioteką nepavyko! \n %s \n , klaida ) ;
grąžinti - 1 ; }

strlen = dlsym ( rankena , 'strlen' ) ;
klaida = dlerror ( ) ;
jeigu ( ! strlen || klaida == NULL ) { printf ( '%s \n , klaida ) ; grąžinti - 1 ; }

printf ( 'Stygos ilgis yra:%d \n , strlen ( src ) ) ;
dlclose ( rankena ) ;
grąžinti 0 ;
}

Mes naudojame šią komandą duotai programai vykdyti. Čia vėliavėlė -lstr naudojama eilutės ilgio funkcijai, o ldl naudojama dlopen bibliotekos failui. Sukompiliuota programa pateikia eilutės ilgį, kaip parodyta apvalkale:

Išvada

Šiame straipsnyje pateikiama informacija apie C kalbos dlopen funkciją. Trumpai pristatome dlopen funkciją. Tada įgyvendinome du pavyzdžius. Funkcija grąžina identifikatorių, kuris apibrėžia atidarytą biblioteką. Tada atidarytoje bibliotekoje esančių funkcijų adresai nustatomi naudojant šį identifikatorių ir funkciją dlsym. Funkcijos adresą bibliotekoje, kuri jau buvo atidaryta naudojant dlopen, galima rasti naudojant funkciją dlsym.