PhantomSync: npm krüptopaketid peidavad rahakoti varastaja

PhantomSync: kaheksa krüptovaluutaarendaja npm-paketti peidavad endas viivitusega, iseenesest püsivat tilgutit

TL; DR

Üks npm-i avaldaja saatis kaheksa väikest paketti, mille nimed kõlasid nagu igapäevased ehitusplokid plokiahela ja rahakoti arendamiseks. base58-utils, abi-encode, eth-dev, arb-kit, layer2-sdk, solana-key-utils, eth-wallet-helpersja crypto-validate-libIgaüks neist sisaldab toimivat utiliiti. Selle utiliidi järele on aga lisatud isetoimiv koodiplokk, mis käivitub mooduli impordi hetkel.

Umbes 37 sekundit pärast importimist, mis plokk dekodeerib paketi sees oleva testimisseadmena maskeeritud kasuliku sisu, kirjutab selle kasutaja kodukataloogi peidetud faili, registreerib end iga kord taaskäivitumiseks login Windowsis, macOS-is ja Linuxis ning käivitab dekodeeritud skripti eraldiseisva protsessina. npm-i installimise ajal ei käivitu midagi; see ootab koodi importimist ja käivitamist, mis on installimisest vaiksem hetk.

Kasulik koormus ei ole läbipaistmatu. See tarnitakse tavalise base64-na, seega "testimisseadme" dekodeerimine taastab teise etapi täielikult: a krüptorahakott ja saladuste varastaja mis ootab masina jõudeolekut, kogub privaatvõtmeid ja seemnefraase, krüpteerib iga leiu kõvakodeeritud RSA-4096 võtmega ning filtreerib selle avalikku IPFS-salvestusruumi kinnitades ja iga 12 tunni järel tagasi suunates.

Me jälgime klastri järgmiselt PhantomSyncKõik kaheksa paketti olid analüüsi ajal npm-i registris saadaval ühe konto all.

Ökosüsteeminpm
Paketidbase58-utils, abi-encode, eth-dev, arb-kit, layer2-sdk, solana-key-utils, eth-wallet-helpers, crypto-validate-lib
Sihitud platvormidWindows, macOS, Linux
PõhikäitumineViivitusega, impordi ajal peidetud dropper testimisseadmena; installib platvormideülese püsivuse
kasulik koormusKrüptorahakott ja saladuste varastaja, RSA-4096 krüpteering, väljafiltreerimine avaliku IPFS-i pinnimise kaudu

Rünnaku anatoomia

Iga pakend tundub esmalugemisel tähelepandamatu. base58-utiliididnäiteks on paar kilobaiti nullsõltuvusega Base58 / Bitcoin-WIF abikoodi – täpselt see, mida nimi lubab. Asjakohane kood asub pärast mooduli moodul.ekspordid, kuhu faili ülaosa libistav lugeja tõenäoliselt ei vaata: ise kutsuv funktsioon, mis ajastab end taimeriga.

Paketi lähtekoodist rekonstrueeritud toimingute ahel näeb välja selline:

1. Package is required() by the host project
2. A self-invoking function schedules a callback ~37,000 ms later (setTimeout)
3. On fire, the callback reads test/fixtures/keypairs.dat (a base64 blob)
4. It base64-decodes that blob into a Node.js script
5. It writes the script to ~/.cache-db/.node-sync/syncd.js (mode 0o700)
6. It installs login-persistence for that script (see below)
7. It spawns "node syncd.js" as a detached process

Kaks disainivalikut paistavad silma.

Kasulik koormus liigub katseseadmena. Teine etapp ei ole kirjutatud ilmselge koodina. See asub test/fixtures/keypairs.dat, base64-fail, mille nimi sulandub paketti, mis väidetavalt haldab võtmepaare. Inimesele, kes tarballi üle vaatab, tundub see näidisandmetena; lisatud koodile on see skript, mida dekodeerida ja käivitada. Tilguti ise ei sisalda võrguaadressi – need asuvad teises etapis –, kuid täiendavat hägustamist pole: kinnitusdetail on üks base64-kiht, seega selle dekodeerimine (base64 -d) taastab täielikult syncd.js ja selle võrgukäitumine. Järgmises osas käsitletakse taastatud etapi tegevust.

Detonatsioon on viivitusega ja seotud impordi, mitte paigaldamisega. Sest päästik on nõuda() pluss ~37-sekundiline taimer installikonksu asemel, käitumine möödub kontrollidest, mis jälgivad ainult npm installi samm ja see viivitus kestab kauem kui paljud lühiajalised liivakasti ja konfiguratsiooniintervalli käivitused. Selleks ajaks, kui midagi käivitub, on paketi hankinud install juba ammu lõppenud.

Kui dekodeeritud skript on kettale salvestatud aadressil ~/.cache-db/.node-sync/syncd.js — tee, mis on valitud lugemiseks nagu tavaline vahemälu kataloog — dropper tagab, et see jääb ellu ka pärast taaskäivitamist kõigil kolmel peamisel platvormil:

  • Linux: cron-kirje, mis käivitab skripti uuesti. Kirje installitakse olemasoleva crontab-faili filtreerimise teel. grep -v syncd, millel on kõrvalmõju, et uus kirje jääb tavalisest loendist välja, mis sama nime puhul grep-i kasutab.
  • Windows: ajastatud ülesanne nimega WinNodeSync, seatud korduma 12-minutilise intervalliga.
  • MacOS: käivitatud töö, millel on märge com.apple.syncd, mis esineb mitmes pakendis – silt, mis jäljendab seaduslikku Apple'i süsteemiteenust.

Seejärel käivitatakse skript kohe eraldiseisva protsessina, nii et see jätkab töötamist ka pärast importimisprogrammi sulgemist.

Mida teine ​​etapp teeb

Kuna kinnitusvahend on üks base64 kiht, dekodeerib teine ​​etapp puhtalt ja seda saab täielikult lugeda. Kõik kaheksa paketti sisaldavad ühte sama skripti kolmest variandist, mis identifitseerib end päisekommentaaris kui phantom syncd v3 — topo durmiente („magav mutt“). Selle ülesanne on varastada krüptovaluuta rahakoti materjali ja arendaja saladusi ning need masinast välja saata. See toimib järgmiste sammudega:

  • 1. Oodake, kuni masin on jõudeolekus. Enne kui midagi ette võtad, syncd.js kontrollib, kui kaua kasutaja on olnud passiivne ja liigub edasi alles siis, kui see ületab teatud läve (umbes 15 minutit) — xprintidle Linuxis ioreg macOS-is HIDIdleTime ja Windowsis PowerShelli jõudeaja päring. Seetõttu kipub andmete kogumine toimuma siis, kui kedagi klaviatuuri taga pole.
  • 2. Hankige kaugjuhtimisega aktiveerimislülitiSkript hangib enne tegutsemist tühjast kohast väikese konfiguratsiooni. Peamine allikas on GitHubi gist-toores URL (gist.githubusercontent.com/juang55/…/cfg.txt); skript aktiveerub ainult siis, kui see konfiguratsioon loeb aktiivne=1Kui sisu pole saadaval, kasutatakse kolme kõvakodeeritud IPFS-sisu identifikaatorit, mis hangitakse avalike lüüside kaudu. gateway.pinata.cloud, ipfs.ioja cloudflare-ipfs.comSee annab operaatorile järelkontrolli sisse-/väljalülitamiseks ja mahavõtmiskindla varuvariandi. (Väikseim variant, tarnitakse ... krüpto-valideerimislib, eth-wallet-helpersja solana-key-utils, millelt on eemaldatud põhikiht ja mis tugineb ainult IPFS-i identifikaatoritele.)
  • 3. Koguge rahakoti materjali ja saladusi. Skript läbib kasutaja kodukataloogi — ~/.config/solana, ~/.ethereum/võtmehoidla, ~/.foundry, ~/.hardhat, ~ / .sshja lauaarvuti/Dokumendid/Allalaadimine (sh hispaaniakeelsed kaustade nimed) ja ~/.env ja shelli rc-failid ning nende ekvivalent AppData asukohad Windowsis. See on suunatud Ethereumi privaatvõtmetele, Bitcoini WIF-võtmetele, BIP-39 seemnefraasidele, Solana võtmepaaridele, Ethereumi võtmehoidla JSON-ile, SSH-võtmetele ja saladust kandvatele keskkonnamuutujatele. Suurem variant (sisse abi-kodeerimine, base58-utiliidid, eth-dev) sisaldab täielikku 2048-sõnalist BIP-39 sõnastikku ja kasutab regulaaravaldisi väljavõte üksikud võtmed ja valideeritud seemnefraasid mis tahes loetud tekstist; kaks väiksemat varianti vastendavad faile hoopis märksõna järgi (seeme, mnemooniline, rahakott, metamask, fantoom, pearaamat, kast, …) ja laadige üles terveid faile.
  • 4. Krüpteerige ja filtreerige avaliku pinnimisteenuse kaudu. Iga leid on komplekteeritud peremehe sõrmejäljega (kasutajanimi@hostinimi, platvorm, ajatempel) ja krüpteeritud skripti manustatud kõvakodeeritud RSA-4096 avaliku võtmega. Seejärel laaditakse krüpteeritud kirje üles, kinnitades selle IPFS-i kaudu api.pinata.cloud/pinning/pinJSONToIPFS, autentitud kõvakodeeritud Pinata API volitustega. Puudub spetsiaalne C2-server, mida arestida: varastatud andmed on pargitud avalikku detsentraliseeritud salvestusruumi, kust operaator saab need saadud sisu räsi abil kätte. Üleslaadimiste vahel on paar sekundit juhuslikku värinat ja kohalik logi ajatempel | võtmetüüp | tagastatud räsi hoitakse aadressil ~/.cache-db/.node-sync/.sl.
  • 5. Jätka ja anna märku 12-tunnise tsükli jooksul. Teine etapp taastab oma püsivuse – cron-kirje Linuxis, a com.apple.syncd macOS-is käivitatud töö ja ajastatud ülesanne nimega Windowsi sõlme sünkroonimine Windowsis – seadistage uuesti käivituma iga 12 tunni järel. Pange tähele, et see on erinev Windowsi ülesande nimi sellest, mille tilguti installib (WinNodeSync); mõlemad on otsimist väärt.

Timeline

Kaheksa paketti avaldati tihedas seerias 13.07.2026 ja 14.07.2026. Mitmel neist on rohkem kui üks versioon; tilguti on versioonide lõikes identne, ainult rea nihked muutuvad vastavalt selle kohal oleva healoomulise utiliidikoodi suuruse muutumisele.

kuupäev sündmus
2026-07-13 Klastri esimesed paketid ilmuvad ühe avaldaja alla (solana-key-utils, eth-wallet-helpers, crypto-validate-lib ja ülejäänud varasemad versioonid)
2026-07-13 → 07-14 Ülejäänud nimed ja järelversioonid avaldatud; samad lisatud dropperid igas
2026-07-14 Kõik kaheksa märgistatud ja analüüsitud; iga paketti saab endiselt registrist installida

Purske ajal muutus kirjastaja registri maine klastri alguses olnud umbes neutraalsest väärtusest tugevalt negatiivseks, kuna tuvastusi kogunes – see on pakettide märgistamise jälgitav kõrvalmõju, mitte kavandatud funktsioon.

Kompromissi näitajad

Kõik allpool olevad näitajad kinnitati analüüsi ajal – need, mis on dekodeerimise teel esitatud „Teise etapi” tabelites. test/fixtures/keypairs.dat ja taastatud teksti lugemine syncd.js.

Failid ja teed

Indikaator Roll
~/.cache-db/.node-sync/syncd.js Dekodeeritud teine ​​etapp, kirjutatud režiimiga 0o700
~/.cache-db/.node-sync/.sl Kohalik väljafiltreerimise logi (ajatempel | võtmetüüp | IPFS-i räsi)
test/fixtures/keypairs.dat Base64-kodeeringuga kasulik koormus, mis on paigutatud tarballi sisse "testimisseadmena"

Teise etapi võrguinfrastruktuur (taastatud syncd.js-ist)

Indikaator Roll
gist.githubusercontent.com/juang55/b298754cb72942b1cdcf02ccd45cde2f/raw/cfg.txt Aktiveerimise tühik; skript käivitub ainult siis, kui konfiguratsioon loeb active=1
Qmcqz3w8j4qFQXDAXAxnrdc2oSX3nzBT4NqtpTqL8mr1ga IPFS-i konfiguratsiooni varuvõimalus (CID)
QmdTXoqVmTHY1i4ZWLdLkoQ9YChp5TXPh5cWXwnAYZt5iF IPFS-i konfiguratsiooni varuvõimalus (CID)
QmfJkLU5gdCpqbbqEjWYC2anXW9FmuEeSLLeLiHVJKYUjp IPFS-i konfiguratsiooni varuvõimalus (CID)
gateway.pinata.cloud, ipfs.io, cloudflare-ipfs.com Konfiguratsiooni varuvariandi toomiseks kasutatavad IPFS-lüüsid
api.pinata.cloud/pinning/pinJSONToIPFS Eksfiltratsiooni lõpp-punkt, varastatud andmed on kinnitatud avalikku IPFS-i
Pinata API võti 13c766575b9270a9825d, kõvakodeeritud väljafiltreerimise mandaat

Teise etapi kogumiseesmärgid (taastatud syncd.js-ist)

Indikaator Roll
~/.config/solana, ~/.ethereum/keystore, ~/.foundry, ~/.hardhat, ~/.ssh, ~/.env, shelli rc-failid Kataloogid/failid, millest otsiti võtmeid ja saladusi
AppData\Roaming\Solana, AppData\Local\ethereum\keystore Otsitud Windowsi vasted
Korjatud artefaktide tüübid ETH privaatvõtmed, Bitcoini WIF, BIP-39 seemnefraasid, Solana võtmepaarid, Ethereumi võtmehoidla JSON, SSH võtmed, salajased keskkonnamuutujad

Püsivuse artefaktid

Platvorm Indikaator
Linux cron kirje käivitamine syncd.js; installitud crontabi kaudu, filtreeritud läbi grep -v syncd
Windows ajastatud ülesanne WinNodeSync (tilguti) ja WindowsNodeSync (teine ​​etapp)
macOS käivitatud silt com.apple.syncd
KÕIK Teine etapp kordub 12-tunnise tsüklina.

Käitumist

  • Ise kutsuv funktsioon lisatakse pärast moodul.ekspordid, ajakava koostamine setTimeout impordi korral ~37 000 ms.
  • lapseprotsess spawn("node", ) eraldatud valikukomplektiga.
  • Teises etapis tühikäigul aktiveerimine (xprintidle / ioreg HIDIdleTime / PowerShelli jõudeaeg; ~15-minutiline lävi).
  • RSA-4096 krüptimise leidmise järel HTTPS POST avalikule IPFS-i kinnitamise API-le.

Paketid ja versioonid (npm, avaldaja solbuilder_io)

Pakend Variandid
base58-utils 1.0.0, 1.0.1, 1.0.3
abi-encode 1.0.0, 1.0.1, 1.0.2
eth-dev 1.0.0, 1.0.1, 1.0.2
arb-kit 1.0.0, 1.0.1
layer2-sdk 1.0.0, 1.0.1
solana-key-utils 1.0.0
eth-wallet-helpers 1.0.0
crypto-validate-lib 1.0.0

kirjastaja

  • solbuilder_io - angel_lopez89[@]proton[.]me, kinnitamata e-posti aadress, kinnitatud allikakontrolli konto puudub, lingitud repositoorium puudub.

Omistamine ja täheldatud käitumine

Kaheksa paketti jagavad ühte avaldajakontot ja ühte kasulikku koormust. Igaüks neist on triviaalne pakett – paar kilobaiti reaalset utiliidikoodi, millele on lisatud sama dropper –, mis on avaldatud ilma lingitud repositooriumita ja kontrollimata ühekordselt kasutatava meiliaadressi all. See ühtsus, jagatud drop-tee, jagatud püsivussildid ja jagatud võtmepaarid.dat klastri ühendavad etapiviisilised failid.

Pakid on oma käitumise suhtes ebatavaliselt avameelsed. solana-key-utils sisaldab lisatud plokki lihtsate sõnadega kirjeldavaid tekstisiseseid kommentaare – üks neist märgistab selle FANTOM: nähtamatu püsivus, teine ​​(hispaania keeles) kõlab järgmiselt Viska ülemine osa taustale, „käivita mutt taustal“. Need on koodi enda märkused selle kohta, mida see teeb; selle postituse kampaania nimi on võetud sellest esimesest sildist koos võltssõlmega „sünkroonimisdeemon“ (sünkroonitud), mida püsivuse mehhanism jäljendab.

Kirjeldame ainult seda, mida kood jälgitavalt teeb. Pakettide nimetamine – kõik krüpto-, rahakoti- ja plokiahela tööriistade terminid – näitab arendajate sihtrühma, kes neid kõige tõenäolisemalt nimepidi tõmbab; see iseenesest ei tuvasta, kes on väljaandja. Teine etapp oli täielikult taastatav base64 kinnitusdetaili dekodeerimise teel ja selle käitumist on kirjeldatud eespool: see kogub rahakoti võtmeid, seemnefraase ja saladusi ning filtreerib need RSA-krüptitult Pinata kaudu avalikku IPFS-salvestusruumi. Märkimisväärne disainivalik on privaatse C2-serveri puudumine – konfiguratsioon saabub GitHubi gistilt ja IPFS-ist ning varastatud andmed pargitakse avalikku detsentraliseeritud salvestusruumi, mis on kodeeritud sisu räsi abil, mida mõlemat on raskem haarata kui ühte ründaja kontrollitud hosti. Kirjutamise ajal ei leitud ühtegi varasemat avalikku aruandlust, mis sobiks selle klastriga.

Kes on paljastatud. Igaüks, kes lisas ühe neist pakettidest Node'i projekti ja seejärel käivitas koodi, mis selle impordib. Kuna detoneerimine toimub impordi, mitte installimise ajal, ei piisa paketi olemasolust üksi – aga iga tavapärane kasutus, mis moodulit laadib, jõuab kasuliku koormuseni. Peibutusnimed on suunatud arendajatele, kes ehitavad üles Ethereumi, Solana, Arbitrumi, Layer-2 ja üldise rahakoti/kodeerimise tööriistade baasil – populatsioonile, kellel on kõige tõenäolisemalt just need varad, mida teine ​​etapp jahib. Igaüks, kes käivitas ühe neist moodulitest masinal, mis hoidis rahakoti võtmeid, seemnefraase, võtmehoidlaid, SSH-võtmeid või... .env saladused peaksid neid volitusi käsitlema ohustatuna ja neid vahetama.

Kaks mustrit, mida tasub omaks võtta. Esiteks kasulik koormus kinnitusvahendina: teise etapi saatmine base64-na usutavalt nimetatud andmefailis (test/fixtures/keypairs.dat) hoiab paketi nähtava lähtekoodi puhtana ja lükkab pahatahtliku sisu faili, mida ülevaatetööriistad ja inimeste poolt ülevaadatud failid sageli inertsete andmetena käsitlevad. Teiseks, impordi ajal viivitatud täitmine platvormideülese püsivusegaPäästiku eemaldamine installikonksult, taimeri lisamine ja seejärel püsimine croni, ajastatud ülesannete ja launchd vahel on teadlik samm eemale lärmakamatest installiskriptide tehnikatest, mida automatiseeritud registri skannimine kõige tähelepanelikumalt jälgib.

Juhised kaitsjatele ja hooldajatele:

  • Lisatud koodi käsitlemine pärast moodul.ekspordid ülevaatuse prioriteedina – tilguti loogika peidab end sageli mooduli „päris” pinna all.
  • Ära eelda, et andmefailid on inertsed. Base64 blob all test/võistluskalendrid/ mis loetakse käitusajal ja dekodeeritakse, on käivitatava failiga külgnev; märgistab käitusajal loetud kinnitusfailid, mis toidavad funktsioon/eval/kirjuta-siis-kudema kett.
  • Otsi langemisrada ~/.cache-db/.node-sync/ ja püsivusühikute jaoks WinNodeSync (ajastatud ülesanne) ja com.apple.syncd (launchd) arendajate masinatel, mis need nimed välja tõmbasid.
  • Hoiatus sõlmeprotsesside kohta, mis loovad cron-kirjeid, ajastatud ülesandeid või käivitatud töid – legitiimsed teegid teevad seda importimisel harva.
  • Eelista lukustusfaile ja kinnitatud versioone ning vaata üle kõigi uute väikeste „utiliidi” sõltuvuste erinevused, eriti avaldatud nullsõltuvusega paketid kinnitamata kontode poolt, millel puudub lingitud hoidla.

Registri kaitsjate jaoks on kokkuvõte see, et installikonksu jälgimine on vajalik, kuid mitte piisav: andmefaili sees paiknev impordiaegne, taimeriga viivitusega dropper läbib ainult installiaegse kontrolli ja püsivuse samm on sageli kõige valjem jälgitav signaal, mida veel püüda.

sca-tööriistad-tarkvara-kompositsiooni-analüüsi-tööriistad
Tarkvarariskide prioriseerimine, leevendamine ja turvamine
Hankige oma tasuta konto.
Krediitkaarti pole vaja.

Turvaline tarkvaraarendus ja -tarne

Xygeni tootekomplektiga