VpnService protect() vagy alkalmazás-kizárás: melyik javítja az útválasztást
Védje az alagutat hordozó socketet, vagy zárja ki az egész alkalmazást: a három feltétel, amely eldönti, mekkora hatókörre van szüksége az Android VPN-jének.
Két módon tarthatja az alagút saját csomagjait az alagúton kívül: védi a szállító socketet, vagy kiveszi az egész alkalmazást a VPN-ből. Ezek különböző problémákat oldanak meg, és a szélesebb választása azért, mert könnyebb bekötni, pontosan az az út, amelyen az alkalmazások észrevétlenül elveszítik a helyi hálózathoz való hozzáférést és a megosztott DNS-t. Kezdje azzal, aminek az alagúton kívül kell maradnia, majd válassza a legkisebb hatókört, amely ezt eléri.
Mit távolít el a protect() az alagútból
VpnService.protect() socketenkénti hívás. Átadja neki azt a socketet vagy leírót, amely az alagutat hordozza, és az Android megjelöli azt a socketet, hogy a forgalma a VPN-interfész helyett az alatta lévő hálózatot használja. Minden más, amit az alkalmazás küld, továbbra is a szokásos VPN-útvonalat követi.
Éppen ez a szűk hatókör a lényeg. A védett socket nem változtatja meg, hogyan oldja fel a neveket a HTTP-kliense, melyik interfészt használják az analitikai hívásai, vagy mi történik egy később megnyitott második kapcsolattal.
Három feltétel, amely meghatározza a hatókört
Az első feltétel, hogy csak az alagút szállításának kell-e kijutnia. Ha az alkalmazás többi forgalmának továbbra is a VPN-en kell átmennie, a socket védelme a helyes hatókör. A második feltétel, hogy Ön irányítja-e a socket létrehozását. Egy könyvtár, amely mélyen belül nyitja meg a saját socketjét, nem hagy helyet arra, hogy meghívja a protect()-t, hacsak nem tesz közzé hookot, vagy nem fogad el előre elkészített socketet. A harmadik feltétel, hogy az alkalmazásnak közvetlenül el kell-e érnie a helyi hálózatot vagy egy captive portalt, ami más követelmény, mint az alagút életben tartása.
Az alkalmazás kizárása a addDisallowedApplication() segítségével a durva eszköz. Minden kapcsolatot eltávolít a VPN-ből, amelyet az alkalmazás létrehoz, beleértve azokat is, amelyeket meg akart vizsgálni, és egyes eszközökön a helyi felderítés viselkedését is megváltoztatja.
Harmadik lehetőség, hogy a szállítást egy kiválasztott hálózathoz köti a bindProcessToNetwork() vagy egy socket szintű hálózati fogantyú segítségével. Ez akkor hasznos, ha az eszköznek egyszerre van Wi-Fi és mobil kapcsolata, és azt szeretné, hogy az alagút egy adott feltöltési csatornán menjen.
Akkor hívja meg, amikor a szállítás létrejön
Hívja meg a protect()-t ugyanabban a blokkban, amely létrehozza a szállítást, a connect() vagy send() előtt. Ha a hívás false értéket ad vissza, zárja be a socketet, és bukjon el a beállítás; a folytatás olyan szállítást hagy Önnek, amelynek csomagjai visszajuthatnak a saját interfészébe.
A forma elég kicsi ahhoz, hogy egy helyen maradjon:
DatagramSocket transport = new DatagramSocket();
if (!protect(transport)) {
transport.close();
throw new IOException("transport not protected");
}
transport.connect(serverAddress);Három részlet harap itt. Először,a boolean az egyetlen jelzés, amit kap, ezért naplózza a hibát elég kontextussal ahhoz, hogy megkülönböztesse a visszavont hozzájárulást az elutasított hívástól. Másodszor,protect() a socketet fedi le, nem a leíró számát: ha bezárja a socketet, és később ugyanazt az egész számot egy másik sockethez használja, az új socket nincs védve. Harmadszor, amikor egy natív könyvtár nyitja meg a szállítást, védje meg a leírót, mielőtt a natív kód csatlakozna, különben lehet, hogy az útvonal már ki van választva.A VpnService-referencia az a hely, ahol megerősítheti, mely túlterheléseket biztosítja valójában a cél API-szintje.
A blokkolt utat tesztelje, ne csak a boldog utat
Az alagút felfelé állapotában ellenőrizze, mert ez az egyetlen állapot, amelyben a két út különbözhet. Küldjön egy kérést a védett szállításon keresztül, és egyet egy olyan kódútról, amely soha nem hívta meg a protect()-t, majd hasonlítsa össze, mit lát a távoli vég: a védett kapcsolatnak az alatta lévő hálózattal mint forrással kell érkeznie, míg a nem védett az alagút saját címét mutatja, és mozgatja az alagút bájtszámlálóit. Az eszközön a ss vagy a netstat ugyanezt a szétválást mutatja, mielőtt bármi elhagyná a rádiót.
A visszavonást külön tesztelje, mert a hozzájárulás változása lerombolja az interfészt anélkül, hogy hozzányúlna a socketkódjához. Vonja vissza a VPN-hozzájárulást, vagy állítsa le a szolgáltatást, építse fel újra a szállítást, és erősítse meg, hogy a protect() továbbra is true értéket ad vissza, és a szállítás újracsatlakozik, amint a hozzájárulást újra megadják.
Ha a védett kérés mégis az alagutat követi, a védelmi hívás valószínűleg azután történik, hogy a socketet már átirányították. Vigye előrébb, és tesztelje újra.
Tartsa a döntést a szállítás beállítása mellett leírva: mely socketek védettek, mely alkalmazásforgalom van kizárva, és mit tesz az alkalmazás, ha a védelem meghiúsul. Ez a sor az, ami megakadályozza, hogy egy későbbi refaktorálás kiterjessze a kizárást az egész alkalmazásra, mert egyetlen teszt meghiúsult. Az is megadja a következő embernek a módját, hogy ellenőrizze a szándékot a manifest visszafejtése nélkül.