•  niereh-światło

Rozdzielacz TCS

Tunel do dzielenia połączenia TCP lub UDP na wiele połączeń TCP

Bramka

Kiedy chcesz podzielić jedno połączenie TCP na wiele? Zwykle używasz tunel osiągnąć dokładne przeciwieństwo . Mój przypadek użycia polegał na obchodzeniu ograniczeń przepustowości w sieci komórkowej, więc testy zostały przeprowadzone z kartą sim, na której nie pozostało już więcej danych[1].

Jak to działa

ten tunel został napisany w golang ponieważ jest wystarczająco szybki i powszechnie używany do narzędzi sieciowych. Cli jest ledwo użyteczne, ponieważ większość opcji została przerobiona, gdy testowałem różne metody.

Początkowo istniały „flings” i „lassos”, które dzieliły liczbę połączeń na wychodzące (odrzucane) i przychodzące (z lasso), ale była to niepotrzebna abstrakcja, ponieważ lepiej oznaczać pakiety ich miejscem docelowym, chociaż głównym celem było oferować różne limity szybkości dla połączeń wychodzących i przychodzących, więc wyższy poziom separacji między górą a dół wydawał się praktyczny.

Klient musi utworzyć instancję wszystkich połączeń, ponieważ zakładamy, że serwer nie może otworzyć połączeń wychodzących. Gdy klienci otrzymują połączenie z aplikacji użytkownika, konfiguruje wymaganą pulę połączeń z serwerem, a wszelkie dane, które otrzymuje, dzieli je między dedykowane połączenia, zgodnie z limitem zdefiniowanym przez użytkownika.

Pakiety są następnie wysyłane do serwera, który musi je zrekonstruować we właściwej kolejności, ponieważ różne połączenia TCP mogą w każdej chwili zakończyć strumień danych (kolejność wysyłania nie jest przestrzegana, ponieważ routing ), a następnie przekazywane do aplikacji odbierającej.

Połączenia są zamykane, a nowe otwierane po osiągnięciu skonfigurowanego limitu danych na połączenie, podobnie jak cienie skarpetkiserwery proxy tunelują dane w różnych strumieniach w celu zamaskowania zachowania strumieni danych, z wyjątkiem tego, że nasz tunel robi to tak często, jak to możliwe.

Dlaczego to działa

Intencją jest tutaj kontrolowanie ilości danych, które powinno obsłużyć każde połączenie. Dla naszych celów nigdy nie było poza tym zwykle jest MTU rozmiar okna. Możesz myśleć o MTU jako o górnej granicy fragmentu danych, który przechodzi w całości przez sieć i był to nasz cel, ponieważ chcieliśmy ominąć ograniczenia przepustowości sieci bramkowanej. Aby ograniczyć ilość danych, przez które może przejść klient, musisz liczyć to, prawda? Jeśli twoja logika działa z czymś takim jakdo-while

Następnie musisz przynajmniej Otrzymaćpacket . Nie jestem pewien, czy tak się faktycznie dzieje, czy też powód, dla którego mój tunel działa, jest inny. Może da się sprawdzić nawet pierwszy pakiet, ale z perspektywy projektowej oznaczałoby to konieczność sprawdzenia każdy pojedyncze połączenie, co osłabiłoby system w przypadku ataków DOS, i tak, mój tunel może być z łatwością wykorzystany jako wydajne narzędzie DOS/Stress, ponieważ możesz podzielić dane na bardzo małe pakiety (co oznacza, że ​​połączenia TCP będą miały dużą presję na ponowne wykorzystanie ) i korzystaj z dowolnej puli połączeń.

Testy na różnych portach wykazały również, że było to możliwe tylko ponad Niektóre portów i że limit stale się różnił między portami, z443 dając jedno z wyższych okien, dookoła20kb , zgaduję, ponieważTLS Uściski dłoni wymagają większej ilości danych i że te limity szybkości będą się zmieniać w zależności od pory dnia[2].

Wyniki

Próbowałem wymazać kodowanie w nadziei na zwiększenie przepustowości danych. Korzystając z biblioteki kodowania wymazywania i enc/dekodując same dane, a także przez nałożenie KCP protokół nad moim protokołem dzielenia. Wypróbowanie KCP może wydawać się podejściem wstecznym, ponieważ zamienia lepsze opóźnienia na niższą przepustowość, ale moim początkowym założeniem było to, że moje wąskie gardło było w połączeniach zerwanych w połowie transmisji, co spowodowałoby wiele uszkodzonych pakietów, więc mogłem osiągnąć wyższy przepustowość z korekcją błędów.

Okazało się, że był to tylko limit szybkości dotyczący liczby połączeń TCP, które klient może wysłać przez sieć, więc po prostu ochrona DOS, z którą nic nie mogę zrobić. Po X ilości połączeń dowolneSYN próby przestają otrzymywać swoje należneACK , wypełniając zaległości i ostatecznie przeciągając tunel. Próby i błędy wykazały, że było to możliwe między4-8[3] połączenia otwarte w dowolnym momencie i z MTU500-1000 przynajmniej bajtów, które można by utrzymać w ciągłym strumieniu128kbps , jeśli stały strumień nie był wymagany, można osiągnąć wyższe prędkości w krótszym czasie dzięki pękanie wiele połączeń na żądanie.

Natomiast (prawda)DNS tunel ledwo może pchać56kbps i może szybko zostać dławiony, ponieważ myślę, że duża liczba żądań DNS wygląda bardziej podejrzanie niż żądania TCP. Musimy sprecyzować, że atrue Tunel DNS koduje (wychodzące) dane w fałszywych subdomenach i dekoduje (przychodzące) dane otrzymane przez odpytywanie rekordów DNS, podczas gdy czasami tunel DNS może być uważany za surowe połączenie UDP przez port DNS, co prawdopodobnie kiedyś w przeszłości służyło do serwerów DNS dozwolone i przekazane poprawnie.

Wnioski

Nie jestem pewien, czy osiągnąłem swój cel pożytek mądrze, ponieważ uruchomienie takiego tunelu może sprawić, że telefon będzie dość gorący i zmarnuje dużo baterii, ale posiadanie go jako zapasowego połączenia może być uspokajające... jeśli rzeczywiście zadałem sobie trud, aby był wystarczająco stabilny :)

[1]zwykle, gdy karta SIM nie ma więcej danych do przeglądania sieci, żądania sieciowe przekierowują do bramy przechwytywania (aby powiedzieć, abyś kupił więcej danych)
[2]Plany mobilnej transmisji danych mogą zapewnić lepsze połączenie w godzinach nocnych
[3]Ta liczba, poniekąd wyrównana do typowej liczby rdzeni, może skłonić Cię do podejrzeń, że jądro w jakiś sposób ogranicza połączenia, scenariusz otwartych połączeń naszego tunelu jest zdecydowanie nietypowy, ale strojenie pokręteł linuksowych nigdy nie dało lepszych wyników z mojej strony.

Tagi postów: