Priklausomybių paieška programoms, kurių priklausomybės nežinomos

Kartais pasitaiko programų, kurios nepateikia aiškių priklausomybių, ypač jei programa įdiegta ne tvarkingu RPM paketu. Užuot bandymų būdu po vieną gliaudę klaidose randamas užuominas apie trūkstamą dar vieną priklausomybę, galime rasti jas visas iš karto analizuojant bibliotekas (SO rinkmenas), kurios pateikiamos su programa.

  1. Apsibrėžiame programos katalogą kaip kintamąjį. Kaip tokios problematiškos programos pavyzdys gali būti pasenusi MATLAB ar MATLAB Compiler Runtime versija, tad toliau pavyzdys analizuojant /usr/local/MATLAB/ kataloge esančias programas (pakeiskite šį kelią į savo programos katalogą):

    TIKRINAMAS_KATALOGAS="/usr/local/MATLAB/"

  2. Išanalizuojame su programa pateiktas bibliotekas ir randame jų priklausomybes:

    find “${TIKRINAMAS_KATALOGAS}” -type f -name ‘*.so*’ -exec readelf -d {} \; | sed -n ’s/.*Shared library:\ \[\(.*\)\].*/\1/p’ | sort -u > priklausomybės_visos.txt

  3. Atsirenkame priklausomybes, kurias pateikia pati programa:

    find “${TIKRINAMAS_KATALOGAS}” -type f -name ‘*.so*’ -printf “%f\n” | sort -u > priklausomybės_pateiktos.txt

  4. Atsirenkame priklausomybes, kurių pati programa nepateikia:

    diff priklausomybės_pateiktos.txt priklausomybės_visos.txt | grep ‘> ’ | cut -c3- > priklausomybės_nepateiktos.txt

  5. Surandame sistemoje esančias bibliotekas.

    • Jei programa yra 64 bitų, tuomet įvykdome:

      find /lib64 -name ‘*.so*’ -printf “%f\n” | sort -u > sistemos_bibliotekos.txt
      find /usr/lib64 -name ‘*.so*’ -printf “%f\n” | sort -u » sistemos_bibliotekos.txt
      find /usr/local/lib64 -name ‘*.so*’ -printf “%f\n” | sort -u » sistemos_bibliotekos.txt
      sort -u sistemos_bibliotekos.txt > sistemos_bibliotekos_visos.txt

    • Jei programa yra 32 bitų, tuomet įvykdome:

      find /lib -name ‘*.so*’ -printf “%f\n” | sort -u > sistemos_bibliotekos.txt
      find /usr/lib -name ‘*.so*’ -printf “%f\n” | sort -u » sistemos_bibliotekos.txt
      find /usr/local/lib -name ‘*.so*’ -printf “%f\n” | sort -u » sistemos_bibliotekos.txt
      sort -u sistemos_bibliotekos.txt > sistemos_bibliotekos_visos.txt

  6. Atsirenkame priklausomybes, kurių nepateikia nei programa, nei dabartinė sistema:

    diff sistemos_bibliotekos_visos.txt priklausomybės_nepateiktos.txt | grep ‘> ’ | cut -c3- > priklausomybės_trūkstamos.txt

  7. Randame RPM paketus, kurie pateikia trūkstamas bibliotekas (ne visoms bibliotekoms gali būti RPM):

    • Jei programa yra 64 bitų, tuomet įvykdome:

      cat priklausomybės_trūkstamos.txt | sed “s/$/\(\)\(64bit\)/” | xargs -n 1 rpm -q –whatprovides > RPM_pateikiantys.txt

    • Jei programa yra 32 bitų, tuomet įvykdome:

      cat priklausomybės_trūkstamos.txt | xargs -n 1 rpm -q –whatprovides > RPM_pateikiantys.txt

  8. Galime įdiegti bibliotekas, kurioms radome RPM paketus:

    grep -v “no package provides” RPM_pateikiantys.txt | sort -u | sed -e :a -e ‘$!N; s/\n/ /; ta’ | xargs sudo zypper in

Net jei ne visoms bibliotekoms pavyksta rasti RPM paketus, programa vis tiek gali veikti. Galite palyginti rezultatus dviejose operacinėse sistemose: senoje, kurioje programa veikė be jokių pranešimų apie trūkstamas priklausomybes, ir naujoje, kurioje jau numatytuoju atveju gali nebebūti diegiamos kai kurios bibliotekos.

Tokiu būdu pavyko rasti, kad senai programai, naudojančiai 32 bitų „MATLAB Compiler Runtime R2012a“, naujoje openSUSE Leap 15.1 sistemoje dar trūko libncurses5-32bit, libICE6-32bit, libSM6-32bit, libXt6-32bit, libXmu6-32bit bibliotekų (priklausomybių buvo ir daugiau). Be jų, paleidžiant matydavosi pranešimai „An Error has occurred while trying to initialize the MCR. The error is: Fatal error loading library <…>: nepavyko atverti bendrojo objekto failo: Toks failas ar aplankas neegzistuoja“ arba:
Unable to initialize com.mathworks.mwswing.MJStartupForDesktop
Unable to initialize com.mathworks.mwswing.MJStartup
Unable to initialize com.mathworks.toolstrip.plaf.TSLookAndFeel
Warning: Initializing Handle Graphics failed in matlabrc.
This indicates a potentially serious problem in your MATLAB setup,
which should be resolved as soon as possible. Error detected was:
MATLAB:Java:GenericException

Aprašytas sprendimas remiasi kodu iš:
https://www.mathworks.com/matlabcentral/answers/358052-is-there-a-list-of-matlab-runtime-dependencies