BSD csomagszűrő

A BPF ( Berkeley Packet Filter ) vagy BSD csomagszűrő egy minimalista kód, amelyet a kernelbe injektálnak , lehetővé teszi a felhasználó számára, hogy hálózati szűrést hajtson végre a kernelben. Különböző verziói (példa: eBPF (kiterjeszteni a Berkeley csomagszűrőt)) során új eszközöket vezettek be a BPF programok előállításának megkönnyítése érdekében. Ezenkívül új felhasználási területek is kiaknázhatóvá váltak, például az eseményfigyelés a kernelben és annak nyomon követése. A mai napig különféle problémák állnak fenn, főként az auditor szintjén.

Meghatározás

Az eredetileg 1992-ben tervezett BPF egy minimalista bináris kód, amelyet a kernelbe injektálnak a felhasználói térből . Lehetővé teszi a felhasználó számára, hogy szűrje a kernelben keringő csomagokat, miközben elkerüli, hogy át kell vinni őket a felhasználói helyre. Minimalista oldala miatt azonban kevés az utasítás, ráadásul a programozási nehézségek miatt kevés alkalmazás használja, például a tcpdump. 2013-ban Alekszej Starovoitov (a Facebook kernelére szakosodott szoftvermérnök) teljesen átalakította a BPF-et új funkciók hozzáadásával és teljesítményének javításával. Ezt az új verziót eBPF-nek hívják, szemben a korábbi verziót jelölő cBPF (klasszikus BPF) -vel. Ez az új nyelv lehetővé teszi a felhasználási esetek sokféleségének megtervezését, amelyek két alkalmazási területre bonthatók. Az első terület a kernel nyomon követése és figyelése, míg a második a hálózati programozás.

Felhasználási eset

Számos felhasználási eset létezik, például nyomkövetés, tároló tűzfalszűrés vagy hálózatépítés, foglalatszűrés , csomagszűrés és forgalomirányítás. Lehetőség van szűrésre a hálózati verem legalacsonyabb szintjén is, vagyis közvetlenül a hálózati interfész kártya illesztőprogramja által. Tehát a csomagokat nagyon korán el lehet dobni; például az XDP (Express Data Path) az eBPF-et használó projekt, amely felhasználható a szolgáltatásmegtagadási támadások megelőzésére . Ezenkívül a BPF-ek lehetővé teszik a hálózati teljesítmény hatékony és rugalmas nyomon követését a virtuális gépek alkalmazásai számára , például a vNetTracer keretrendszer.

Itt van a GMP-ket használó projektek nem teljes listája:

Nyomon követés / figyelés:

Bpftrace egy magas szintű plotter nyelv a Linux Berkeley csomagszűrők (eBPF) fejlesztésére, elérhető a linux kernel legújabb verzióiban (azaz a 4.x verzió óta). Ezenkívül a bpftrace az LLVM-et használja a szkriptek összeállításához, és a BCC-t használja a linux BPF rendszerrel való interakcióhoz. Tökéletes egy olyan rendszer teljesítményelemző eszköz, amelyet a Linux kernel fejlesztői közösség fejlesztett ki. Ply egy könnyű dinamikus nyomkövető eszköz, a libc-n kívül más függőséggel nem rendelkezik. Támogatja az x86_64 arch64, az arm és a powerpc architektúrákat. Összeállítja a szkripteket egy BPF programba, és a C-hez hasonló szintaxist használ. Systemtap egy nyomkövető / szondázó eszköz, a GPL engedélyével , amely lehetővé teszi az újrafordítás, telepítés és újraindítás megkerülését az adatgyűjtés érdekében. Van parancssori felülete, valamint szkriptnyelve. PCP a "Performance Co-Pilot" kifejezés. Ez egy kiforrott, bővíthető, platformokon átívelő eszközkészlet, amely lehetővé teszi a rendszer élő és retrospektív elemzését. Weave Scope egy eszköz a Docker konténer valós idejű felügyeletéhez és vezérléséhez. Nézetet kínál a mutatókról, a címkékről és a tárolók metaadatairól; valamint a konténerek kezelése.


Hálózat:

Cilium egy nyílt forráskódú szoftver, amely biztosítja és biztosítja a hálózati és terheléselosztási kapcsolatokat az alkalmazás konténerei vagy folyamatai között. Be van építve a Kubernetes és a Mesos hangszerelési keretrendszerbe . Suricata egy hálózati behatolás-észlelő rendszer, egy behatolás-megelőző rendszer és egy hálózati biztonsági ellenőrző eszköz. Systemd egy sor programkezelés a linux kernel rendszerkezeléséhez. Iproute2 egy nyílt forráskódú szoftver, amely segédprogramokat biztosít a hálózat irányításához és felügyeletéhez a linux kernelben. P4c-xdp egy P4 kód háttér-fordító az XDP számára.


Egyéb:

LLVM egy C kód fordító az eBPF programban. BCC a BPF Compiler Collection mellett áll, egy eszköztár a kernel nyomon követésére és kezelésére szolgáló hatékony programok megírásához. Ezenkívül a BCC megkönnyíti a BPF programok írását, a kernel C-ben történő programozásával, valamint a Python és a Lua front- endjeivel . Libbpf egy BPF könyvtár, amely lehetővé teszi a BPF programok betöltését az LLVM által előállított ELF formátumban a kernelbe. Bpftool az eBPF programok ellenőrzésének és manipulálásának eszköze. Gobpf egy GO könyvtár, amely lehetővé teszi a BCC eszköztár számára, hogy eBPF programokat állítson elő GO kódból. Ebpf_asm az eBPF programok összeállítója, hasonló szintaxissal írva, mint az Intel.

Műszaki üzemeltetés

A BPF CFG vezérlő folyamatábrákat használ a csomagelemzésben használt kritériumok, valamint a famodell- kifejezések teljesítményének bemutatására . Ezenkívül a BPF ezeket a grafikonokat használja szűrési szabályok felállítására, amelyek lehetővé teszik a csomag elemzéséhez és a redundáns összehasonlításokhoz szükséges CFG útvonalak hatékony csökkentését. A rendszerhívások által végrehajtott adatátvitel kétirányú módon történik a kernel és a felhasználói tér között. Ezek lehetővé teszik az eBPF bináris kódnak a kernelbe történő injektálásának megfelelő előrehaladását, valamint az adatok kommunikációját a cél kernelből a felhasználói tér folyamatába. A BPF program által társított csomagokat részben átmásolják egy pufferbe, mielőtt átkerülnének a felhasználói helyre. A BPF lehetővé teszi a program számára, hogy meghatározza a pufferbe másolandó csomag bájtjainak számát. Ez időt takarít meg azzal, hogy elkerüli a felesleges adatok másolását. Például TCP / IP / Ethernet csomagokhoz 134 bájt elegendő. Az a program, amely statisztikákat kíván készíteni a TCP keretekről, csak a keretek egy részét képes lemásolni, ezzel megtakarítva a végrehajtási időt.

Az eBPF a BPF kiterjesztése, amely több szempontból is különbözik tőle: a programokat a felhasználó tölti be, és ellenőrzik a program megszüntetését annak biztosítása érdekében, hogy biztonságos legyen a futtatása. Az eBPF legújabb kiterjesztése a megosztott adatstruktúrákhoz való hozzáférés képessége. Valójában az adatok megosztása érdekében az eBPF három különböző mechanizmust használ:

Mivel a Linux kernel 3.15-ös verziója, az eBPF virtuális gép funkciói az alaputasításokkal és az új eBPF-funkcionalitások bevezetésével linkréteg-hozzáférést biztosítanak, ez lehetőséget teremt a szűrésre és a szűrésre. Elemezze a hálózati csomagokat. Az eBPF programokat azonban meg lehet hívni a hálózati verem különböző rétegeiben, amely lehetővé teszi az elfogott csomagok feldolgozását, mielőtt továbblépne a következő rétegre. Az EBPF a natív CPU utasításokba fordított bináris kódra támaszkodik, amikor a kiterjesztést betöltik a kernelbe. Ellentétben a klasszikus bájtkóddal, például a Java-val, az eBPF fordítója és végrehajtási ideje nem ír elő semmilyen típusú vagy memóriabiztonságot. Ehelyett a biztonságot egy statikus hitelesítő javítja, amely ellenőrzi, hogy a program nem fér hozzá a kernel adatszerkezeteihez, vagy oldalhibákat okozhat.

Biztonsági és stabilitási kockázatok vannak, amikor a kódot végrehajtják a kernelben. E kockázatok csökkentése érdekében a BPF tolmácsra támaszkodik a program biztonságos végrehajtásához. E kockázatok csökkentése érdekében az eBPF bevezet egy Linux verifikátort, amely biztosítja, hogy minden program megfeleljen bizonyos feltételeknek, mielőtt betöltenék a kernelbe, elkerülve ezzel az ellenőrzési idő magas költségeit. Biztosítja, hogy a program képes legyen befejezni, hogy ne tartalmazzon olyan hurkot, amely a kernel összeomlását okozhatja, vagy hogy bizonyos utasítások nem érhetők el. Egy másik időpontban minden egyes utasítást ellenőriz és szimulál, hogy megbizonyosodjon arról, hogy a regiszterek és az elemek állapota érvényes-e, megakadályozva ezzel a memóriához vagy a kernel kiosztott területén kívüli állapotához való hozzáférést. Az eBPF implementáció biztosítja, hogy biztonságos és biztonságos legyen a kernel számára, ugyanakkor lehetővé teszi a kernelben a különböző munkák beállítását, például a kernel nyomon követését és a hálózat létrehozását.

A rendszerhívások lehetővé teszik a bináris kód betöltését. A feltöltés sikeres végrehajtásához a programot az eBPF hitelesítőjének kell igazolnia. Az EBPF programok egyszerre, akár különféle kampókon is példányosíthatók. Tehát külön-külön is működhetnek, vagy láncolhatók.

Hálózatok

A BPF program egy interfészen hallgathat, amikor ez megtörténik, az illesztőprogram meghívja először ezt a programot. Ezután a BPF elosztja a csomagokat a feldolgozásban részt vevő minden egyes szűrőnek. Ezután a felhasználó által definiált szűrők alkalmazódnak a csomagokra, és eldönthetik, hogy a csomagot elfogadják-e vagy sem, és hány bájtot kell menteni az egyes csomagokból. A BPF minden egyes szűrőhöz a kért mennyiségű adatot másolja pufferként társítani. ezt a szűrőt. A topológia módosításakor vagy az alkalmazások változásakor szükségessé válik a tűzfalként szolgáló szabályok módosítása annak érdekében, hogy hozzá lehessen adni, törölni vagy módosítani lehessen a szűrők által érintett portokat és címeket. Ehhez a bittérkép stratégiának köszönhetően, amely egyszerűvé teszi a C programot, csak hozzon létre egy új programot új térképekkel, töltse be a térképet új kulcsértékekkel, és cserélje le a régivel. iptables-restore.

Eszközök

Jit össze

A szűrőket bájtkódként értelmezik egy tolmácsos kernben. Ennek hiányában az eBPF használhatja a kern on-the-fly fordítóját (JIT fordító) az eBPF által előállított byte-kódok natív kódra történő lefordítására és opcionális gépfüggő optimalizálások végrehajtására.

LLVM

A Clang (natív LLVM) lehetővé teszi a felhasználó számára, hogy C kódját egy ELF fájlban egy eBPF utasításba fordítsa.

BCC

Az eBPF utasításokban történő programozás bonyolult lehet. Ezért létezik egy BPF Compiler Collection (BCC) nevű eszköztár, amely lehetővé teszi a felhasználó számára, hogy egyszerűen létrehozhasson eBPF programokat. A BCC felöleli és továbbfejleszti az LLVM-et, hogy a felhasználó számára lehetővé tegye az eBPF-térképek C-kódban történő meghatározását és a C-kód összeállítását eBPF-programba.

Utasítás

A BPF + virtuális gépnek 5 működési osztálya van:

Fejlesztések és korlátozások

2019-ben még számos probléma merül fel a fejlesztő számára, például:

Korlátozások vannak a kernelszolgáltatások használatában, kevés a segítő funkció, és az eBPF programokban nem használható felhasználói terület vagy harmadik féltől származó szolgáltatás. Bizonyos megszorítások rugalmassá teszik a programellenőrzéseket, és lehetővé teszik a rendszer integritását, például a dinamikus allokációk, a kernel adatszerkezeteihez való hozzáférés, a kernel API-k hívása vagy az ugrási utasítások képtelenek közvetetté tenni. Valamint az a tény, hogy egyetlen szálon futtatják, és ezért az utasítások számához kapcsolódik egy végrehajtási idő.

BPF teljesítmény

A cGMP olyan megvalósítási stratégia puffert használ, amely teljes teljesítményét akár 100-szor gyorsabbá teszi, mint az ugyanazon a hardveren futó NIT (Network Interface Tap ) SUN. A BPF-hez való hívás végrehajtási ideje csomagonként körülbelül 6 mikroszekundum egy olyan csomag esetén, amely eldobja az összes csomagot. Az EBPF-ek akár négyszer gyorsabbak az x86_64 architektúrákon, mint a cBPF-megvalósítás egyes hálózati szűrő mikrobarátoknál, és a legtöbb 1,5-szer gyorsabb. Az eBPF-ek teljesítményének 10-szeres javulása van az IPTABLES és az NFTABLES-hez képest.

Előmag (XDP)

Az XDP, amely a hálózati verem legalacsonyabb szintjéhez van csatlakoztatva, durva csomagszűrésre alkalmas, például a szolgáltatásmegtagadási támadások megelőzésére . Négyszeres teljesítményt képes produkálni a kernel hasonló feladatához képest. Ezen túlmenően az XDP a JIT (Just In Time) kódfordítás használatával is javítja a középső késleltetést, akár 45% -os teljesítmény-javulást eredményezhet a magasabb kiugró késési értékek költségével. Az XDP kompromisszumot kínál, nem kínál olyan jó teljesítményt, mint a kernelt felülíró nagy teljesítményű dedikált keretrendszerek. De kernelintegrációt kínál, ami azt jelenti, hogy a csomagok minden előnyével át tudnak menni a hálózati veremben. Bár csak egy 10 GbE-s vonal átbocsátásának 50% -át kezeli, ez egyetlen mag teljesítményét jelenti, vagyis skálázódik a CPU-magok számával.

BPF előzmények

A BPF eredetileg a „Berkeley csomagszűrő” kifejezést jelenti, amelyet 1992-ben fejlesztettek ki az UNIX számára a hálózati csomagok szűrése céljából, majd lehetővé teszik a hálózati felügyeleti alkalmazások, például a „tcpdump” teljesítményének javulását. A BPF-nek nem az a feladata, hogy eldobja a fogadott csomagokat, de szűrőként leírva csomagokat társíthatnak, csomagokat másolhatnak és csomagokat küldhetnek.A kezdetben a BPF-eket a 2 regiszteres linux 2.x kernelben implementálják 32 Ezután Alekszej Starovoitov 2013-ban javaslatot tett a BPF javítására, amely most megkülönbözteti a cBPF-t (klasszikus BPF) és az eBPF (kibővített BPF), az egyik legjelentősebb változás a 10 64 bites regiszterbe való átjutás, valamint a kernelben lévő függvényhívás egy új utasításnak köszönhetően. Egy másik különbség az, hogy nincs állapotállandóság a cBPF-ben míg az eBPF-ben az állapotok fenntarthatók a térképeknek köszönhetően, az eBPF-ek a 3. verzióban jelennek meg .x a linux kernelből, folyamatos fejlesztésekkel, például egy JIT (Just In Time) fordítóval, új funkciókkal, például a „maps” és a „tail hívások”.

Referencia

  1. Monnet 2016
  2. Chaignon 2018
  3. Suo 2018
  4. Scholz 2018
  5. Cilium Szerzők 2019
  6. bpftrace
  7. perf
  8. réteg
  9. systemtap
  10. PCP
  11. Weave Scope
  12. Cilium
  13. Suricata
  14. rendszerd
  15. iproute2
  16. p4c-xdp
  17. LLVM
  18. BCC
  19. libbpf
  20. bpftool
  21. gobpf
  22. ebpf_asm
  23. McCanne 1993
  24. Lidl 2002
  25. Baidya 2018
  26. Saif 2018
  27. Ellis 2017
  28. Belkalem 2018
  29. Nam 2017
  30. Gershuni 2019
  31. Fleming 2017
  32. Miano 2018
  33. Deepak 2018
  34. Begel 1999
  35. Tu 2018
  36. Van Tu 2017
  37. Toy 2015
  38. Corbet 2014
  39. Toy 2017
  40. Bos 2004

Bibliográfia

Weboldal

Lásd is