Priklausomybė-Sumišimas-Versija-Prisegimas

Versijų prisegimo trūkumas ir priklausomybių painiava

Kurdami programinę įrangą, mes esame priklausomi tiek nuo savo, tiek nuo trečiųjų šalių komponentų arba artefaktų. Lankstus priklausomybių valdymas yra būtinas šiuolaikinei programinei įrangai. Paketų tvarkyklės, tokios kaip NPM, Specialistė, pieputis or „NuGet“ dažnai naudojami programinės įrangos priklausomybėms nurodyti. Šie įrankiai buvo sukurti atsižvelgiant į patogumą ir naudojimo paprastumą, o ne į saugumą.

 

Problema

Problema ta, kad lankstumas ir naudojimo paprastumas kūrėjams daro blogus veikėjus, kurie programinės įrangos priklausomybes laiko nenugalimu žavesiu savo verslui. Rezultatas: blogo būdo veikėjai pasinaudojo visais čia parodytais įmanomais atakų keliais. Šaltinis: „Backstabber's Knife Collection: A Review of Open Source Software Supply Chain Attacks“

Šiame įraše daugiausia dėmesio skirsime atvirų versijų deklaracijų naudojimui ta prasme, kad atsisiųsta versija nėra fiksuota, o turi priklausyti tam tikram diapazonui. Kompiliavimo metu paketų tvarkyklė pasirenka ir atsisiunčia / įdiegia naujausią esamą versiją, suderinamą su nurodytu versijų diapazonu.

Iliustruokime atviras deklaracijas skirtingų paketų tvarkyklių priklausomybių deklaracijose:

      • NPM: paketas.json

    {

     

       ...

       „priklausomybės“: {
          ...
          „priima“: „>=1.3.8“,
          „lodash“: „~4.16.0“,
          ...
       },
       ...
    }

    Bus įdiegta didžiausia esama „accepts“ paketo versija, ne senesnė nei 1.3.8, taip pat didžiausias „lodash“ pataisų atnaujinimas 4.16.x versijoje.

        • Maven: pom.xml

      ...

      ...

           commons-io
           commons-io
           IŠLEIDIMAS

      ...

      ...

      Paskutinė prieinama „commons-io“ (jar failo) versija bus pridėta kaip priklausomybė.

          • Pip: setup.py

        ...
        setup (
            ...
            install_requires=['pipirų', 'launchpadlib'],
            ...
        )
        ...

        Tokios atvirų versijų schemos turi gerąją ir blogąją puses. Geroji pusė yra ta, kad naujesnės versijos paprastai yra funkcinių ir kokybės patobulinimų, klaidų ištaisymų ir saugumo pataisų, kurios atnaujinamos automatiškai. Atkreipkite dėmesį, kad daugumos realių projektų atveju pataisymai nėra perkeliami į ankstesnes nedideles versijas, išskyrus galbūt katastrofiškus saugumo pažeidžiamumus. Atviros versijos taip pat tinka naudoti bibliotekose, siekiant sumažinti versijų, kurias reikia įdiegti, skaičių, kai pašalinamos visos priklausomybės.

        Tačiau atvirų versijų diapazonai turi ir trūkumų. Kompiliavimo metu tiksliai nežinote, kurios versijos bus įdiegtos, o kompiliavimo versijos nėra kartojamos. Taip pat yra... tamsus pusė su atviromis versijomis. Jei piktavalis veikėjas sugeba viešoje saugykloje paskelbti kenkėjišką komponentą su aukšta versija, suderinama su jūsų atviruoju diapazonu, jūsų kitoje versijoje bus kenkėjiškas komponentas, galbūt net diegimo scenarijuose bus vykdoma kenkėjiška programa, kuri gali būti vykdoma automatiškai. Atakos naudingosios apkrovos užmaskavimas yra savotiškas menas.

        Tai vadinama Versijos prisegimo trūkumas klausimas.

        Blogi veikėjai visada bando įdiegti kenkėjiškas populiarių atvirojo kodo paketų versijas. Jie gali gauti prieigą prie paketų saugyklų raktų slapta nutekėjimo būdu; jie dažnai naudoja socialinę inžineriją arba slepia įdėtą kenkėjišką priklausomybę iš pažiūros naudingoje vietoje. pull requestNet keli autoriai vieną dieną nusprendžia, kad pasaulis nėra teisingas, ir kandžiojasi savo klientus... protesto programinė įranga savo pakuotėse!

        Įsivaizduokite, kad dirbate organizacijoje, kuri naudoja vidinius komponentus ir atvirojo kodo.
        Jei piktavalis veikėjas žino tokių vidinių komponentų pavadinimus, jis/ji gali publikuoti komponentą tuo pačiu pavadinimu viešojoje saugykloje. Daugelis paketų tvarkyklių pirmiausia gauna viešuosius komponentus, ir jei versija tinkamai pasirinkta, o deklaruotoje priklausomybėje esanti versija yra atvira, – puiku! Ši problema pavadinta Priklausomybės painiava.

        Pateiksime pavyzdį. Tarkime, kad mūsų NPM projekte turime priklausomybę nuo privataus komponento:

            • NPM: paketas.json

          {
            „pavadinimas“: „mano-projektas“,

           

            ...
            „priklausomybės“: {

              ...
              „my-private-dep“: „>=1.0.0“,

              ...

             }

             ...

          }

           

          Užpuolikas gali sukurti didelę „my-private-dep“ versiją (pvz., 99.0.0) ir paskelbti ją viešojoje „npm“ saugykloje su savo netikra paskyra (užpuolikui nereikia nieko daryti su „my“ organizacija). „NPM“ paketų tvarkyklė įdiegs kenkėjišką priklausomybę, dažnai su pražūtingais rezultatais.

          sprendimas

          Norėdami išvengti šių problemų programinės įrangos kūrimo procese, turėtume laikytis griežtų normų, kaip deklaruoti komponentų versijas, kurios priklauso nuo naudojamos technologijos. Svarbu tai, kad konkreti paketo versija, paskelbus ją saugykloje, būtų nekeičiama (siekiant išvengti priklausomų komponentų sugadinimo, ne tik dėl saugumo priežasčių).

          Bendra idėja yra fiksuoti (pin) versijas, visada tikrinant, ar pataisytose komponentų versijose (įskaitant VISAS tranzityvias priklausomybes) nėra kenkėjiškų programų, ir tai įmanoma dėl užrakinimo failai kurį siūlo daugelis paketų tvarkyklių. Pažiūrėkime, kaip versijų prisegimas veikia skirtingose ​​paketų tvarkyklėse. Yra subtilus kompromisas tarp dažni versijų atnaujinimai žinomų pažeidžiamumų taisymui ir versijos prisegimas siekiant išvengti nedeterministinių kompiliacijų ir galimų tiekimo grandinės atakų.

              • NPM:
                „npm“ arba „yarn“ paketų tvarkyklės naudoja skirtingus užrakinimo failus (atitinkamai „npm-shrinkwrap.json / package-lock.json“ arba „yarn.lock“), kuriuose pateikiamos fiksuotos visų priklausomybių, tiek tiesioginių, tiek netiesioginių, versijos. Užrakinimo failai turėtų būti versijų kontroliuojami, kitaip kiti kūrėjai / kūrimo mazgai gali baigti darbą su skirtingomis versijomis. Venkite „npm“ diegimo, nebent kūrimo metu reikia atnaujinti priklausomybes (pvz., norint įdiegti saugos pataisas). Paprastai naudokite deterministiškesnį „npm ci“ (švarų diegimą), nes paketų tvarkyklė naudos užrakinimo failą arba nutrauks darbą su klaida, jei užrakinimo failo nėra arba jis neatitinka „package.json“. Jei išvardytos versijos buvo patikrintos dėl kenkėjiškų programų, užrakinimo failas užtikrina, kad kūrimo metu nieko blogo nenutiks.

                Vidiniams komponentams rekomenduojama sukurti NPM taikymo sritis organizacijos valdomas (pvz., @myorg) ir naudoti tą taikymo sritį priklausomybėje (pvz., @myorg/my-private-dep), kuri gali turėti tik privatų matomumą. Tai blokuoja priklausomybės painiava atakų, nes tik organizacijos narys, turintis rašymo prieigą, gali publikuoti paketus pagal tokią taikymo sritį.

              • Specialistė:
                „Maven“ / „Gradle“ neturi užrakinimo failų (bet žr. šis „StackOverflow“ straipsnis).

                Versijų diapazonai su „Maven“ / „Gradle“ nenaudojami taip dažnai, kaip su kitomis ekosistemomis. Tiesiog venkite versijų diapazonai ir NAUJAUSIOS arba IŠLEIDŽIAMOS metaversijos. Taip pat reikėtų patikrinti netiesiogines versijas. „Maven“ papildinio versijos yra puiki versija kontrolės priemonė.

                Atkreipkite dėmesį, kad „Maven“ visada turėjo organizacijos apimties koncepciją („groupId“ priklausomybės dalį), ir priklausomybių painiava šiai ekosistemai, regis, visai nėra problema.

              • pieputis:
                „Python“ kalboje yra įvairių įrankių, skirtų užrakinimo failams tvarkyti:

                - pipenv, kuris sugeneruoja „Pipfile.lock“ užrakinimo failą.
                - poezija, kuris generuoja poetry.lock.
                - pip užšaldymas, komanda, kuri sugeneruoja failą „requirements.txt“, kuris veikia kaip užrakinimo failas. Patikrinkite, ar visos priklausomybės naudoja fiksuotas versijas, naudodami operatorių ==. Tada „pip install -r requirements.txt“ naudoja fiksuotas priklausomybes.

            Priminkite, kad aukščiau pateikti užrakinimo failai turėtų būti versijų kontrolėje ir kad pasirinkta kūrimo komanda turėtų naudoti užrakinimo failą.

            Įprasta paketų saugykla, naudojama su „pip“ (PyPI), neturi pavadinimų taikymo sričių ir yra pažeidžiama priklausomybių painiavos atakų. Kaip išvengti painiavos dėl priklausomybių Python ekosistemoje nėra lengva, ir kai kurie autoriai rekomenduoja naudoti vidinę saugyklą, kuri veiktų kaip viešųjų priklausomybių, gautų iš PyPI, tarpinis serveris, bet pirmiausia paimti privačias priklausomybes iš vidinės saugyklos („-index-url“ turėtų nurodyti į vidinę saugyklą, o ne į PyPI, o „-extra-index-url“ turėtų būti pašalintas).

            Keletas tikrų išpuolių

            „Getcookies“ atakaVeikėjas dustin87 į populiarųjį „npm mailparser“ paketą pridėjo netiesioginę priklausomybę nuo kenkėjiško paketo su RCE galiniu prievadu (gCOMMANDhDATAi):

            JSON.stringify(req.headers).replace(/g([a-f0-9]{4})h((?:[a-f0-9]{2})+)i/gi, (o, p, v) => {})

            Nors „mailparser“ nebenaudojamas (nėra recenzentų!), jis vis tiek sulaukė apie 64 000 atsisiuntimų per savaitę. Tai buvo beveik neįvykusios atakos atvejis, nes RCE nebuvo realiai naudojamas.cisED.

            Paskelbta NPM šis pranešimas su išsamia informacija apie „getcookies“ ataką.

            Priklausomybės painiava:

            Alexas Birsanas 2021 m. atrado priklausomybės painiavos problemą ir paskelbė įrašą pavadinimu „Kaip įsilaužiau į „Apple“, „Microsoft“ ir dešimtis kitų įmonių".

            Atminkite, kad npm atveju organizacijos taikymo sritis, pvz., @myorg, turėtų būti rezervuota, o vidiniai paketai turėtų būti modifikuoti, kad būtų galima naudoti šią taikymo sritį.

            Naudojant „pip“, bendras viešasis registras „PyPI“ neturi sričių / vardų erdvių. Kiekvienas privatus paketas gali turėti viešąjį paketą „squat“ su tuo pačiu pavadinimu kaip ir vidinis paketas, bet tuščią ir galbūt generuojantį klaidą naudojant, kad jį būtų galima atpažinti, jei jis netyčia būtų iškviestas.

            Node-ipc:

            Prasidėjus Rusijos ir Ukrainos karui, paketo savininkas įdiegė kenkėjišką kodą, skirtą atsitiktinių failų šalinimui, kai jis buvo įdiegtas Rusijos ir Baltarusijos kompiuteriuose. Failas ssl-geospec.js atliko tokį geografinį skirtumą:

            Įdomu tai, kad kituose paketuose, pavyzdžiui, populiariojoje „Vue.js“ sistemoje, buvo naudojamos atvirosios „node-ipc“ priklausomybės versijos, o jos kūrėjai gavo skubus apeliacinis skundas prisegti „node-ipc“ priklausomybę prie saugios versijos.

            tai įraše yra daugiau informacijos dėl šio sabotažo, kuris žengia dar toliau nei kiti Protestavimo įranga Problemos.

             

            Baigiamosios pastabos

            Atviros versijos turėtų niekada būti naudojami konsoliduotuose programinės įrangos projektuose. Jie padaro versijas neatkartojamas, o užpuolikai gali jas išnaudoti ir sugebėjo įdiegti kenkėjiškas programas per atakas į priklausomybių medžius, kaip minėta priklausomybių painiava.

            Neteisingos konfigūracijos, pvz. atviros versijos, versijos neprisegimo nebuvimas arba neapibrėžti vidiniai komponentai reikėtų vengti. Pirmiausia reikia aptikti tokias problemas, galbūt net užblokuoti kūrimą, kai jos randamos, ir standartizuoti veiksmų protokolą.

            Automatinis priklausomybių trūkumų ir konfigūracijos klaidų aptikimas, pranešant apie įtartinas priklausomybes, kurios gali būti pažeidžiamos konkrečių tiekimo grandinės atakų, pvz. priklausomybės painiava, visa tai su veiksmingais taisymo įrankiais, yra vienas iš pagrindinių tikslų „Xygeni“ platforma.

            Norėdami paskaityti daugiau
            Ohm M., Plate H., Sykosch A., Meier M.: „Backstabber's Knife Collection: A Review of Open Source Software Supply Chain Attacks“ (liet. „Atvirojo kodo programinės įrangos tiekimo grandinės atakų rinkinys“). DIMVA 2020. Paskaitų užrašai kompiuterių moksle, t. 12223. Springer – 2020 (priklausomybių atakų medžio paveikslo šaltinis).
            @adam-npm: „Pranešta apie kenkėjišką modulį: getcookies„.npm tinklaraštis (archyvuotas) – 2018 m. gegužės 2 d.“
            Aleksas Birsanas: „Kaip įsilaužiau į „Apple“, „Microsoft“ ir dešimtis kitų įmonių„.“ Vidutinė – 2021 m. vasario 9 d.
            Axas Sharma: „DIDELIS sabotažas: garsusis npm paketas ištrina failus protestuodamas prieš karą Ukrainoje„BleepingComputer“ – 2022 m. kovo 17 d.

            sca-tools-software-composition-analyses-tools
            Prioritetizuoti, pašalinti ir apsaugoti savo programinės įrangos rizikas
            Gaukite nemokamą paskyrą.
            Nebūtina kreditinės kortelės.

            Apsaugokite savo programinės įrangos kūrimą ir tiekimą

            su „Xygeni“ produktų rinkiniu