Szybkość, z jaką mój serwer może akceptować () nowe połączenia przychodzące TCP, jest naprawdę zła w Xen. Ten sam test na metalowym sprzęcie pokazuje przyspieszenie 3-5x.
- Dlaczego to takie złe pod Xenem?
- Czy możesz dostosować Xen, aby poprawić wydajność dla nowych połączeń TCP?
- Czy istnieją inne platformy wirtualizacji lepiej dostosowane do tego rodzaju przypadków użycia?
tło
Ostatnio badam pewne wąskie gardła w wydajności własnego serwera Java działającego pod kontrolą Xena. Serwer mówi HTTP i odbiera proste połączenia TCP / żądania / odpowiedzi / rozłączenia TCP.
Ale nawet podczas wysyłania dużej ilości ruchu do serwera, nie może zaakceptować więcej niż ~ 7000 połączeń TCP na sekundę (w 8-rdzeniowej instancji EC2, c1.xlarge z uruchomionym Xen). Podczas testu serwer wykazuje również dziwne zachowanie, w którym jeden rdzeń (niekoniecznie procesor 0) jest bardzo obciążony> 80%, podczas gdy inne rdzenie pozostają prawie bezczynne. To prowadzi mnie do wniosku, że problem związany jest z wirtualizacją jądra / bazowego.
Podczas testowania tego samego scenariusza na platformie bez systemu wirtualnego otrzymuję wyniki testu pokazujące szybkość akceptacji TCP () powyżej 35 000 / sekundę. To na maszynie Core i5 4 Core z systemem Ubuntu ze wszystkimi rdzeniami prawie całkowicie nasyconymi. Wydaje mi się, że ta postać jest odpowiednia.
W instancji Xen ponownie próbowałem włączyć / dostosować niemal wszystkie ustawienia w sysctl.conf. Włączając włączanie funkcji odbierania sterowania pakietami i odbierania sterowania przepływem oraz przypinania wątków / procesów do procesorów, ale bez widocznych korzyści.
Wiem, że podczas działania zwirtualizowanego należy oczekiwać obniżonej wydajności. Ale do tego stopnia? Wolniejszy serwer typu bare-metal przewyższający virt. 8-rdzeniowy 5 razy?
- Czy to naprawdę oczekiwane zachowanie Xen?
- Czy możesz dostosować Xen, aby poprawić wydajność dla nowych połączeń TCP?
- Czy istnieją inne platformy wirtualizacji lepiej dostosowane do tego rodzaju przypadków użycia?
Odtwarzanie tego zachowania
Po dokładniejszym zbadaniu tego problemu i wskazaniu problemu dowiedziałem się, że narzędzie do testowania wydajności netperf może symulować podobny scenariusz. Za pomocą testu TCP_CRR firmy netperf zebrałem różne raporty z różnych serwerów (zarówno zwirtualizowanych, jak i innych niż virt). Jeśli chcesz przyczynić się do niektórych ustaleń lub przejrzeć moje bieżące raporty, zobacz https://gist.github.com/985475
Skąd mam wiedzieć, że ten problem nie wynika z źle napisanego oprogramowania?
- Serwer został przetestowany na czystym sprzęcie metalowym i prawie nasyca wszystkie dostępne mu rdzenie.
- Podczas korzystania z utrzymywanych połączeń TCP problem zniknął.
Dlaczego to jest ważne?
W ESN (mój pracodawca) jestem kierownikiem projektu Beaconpush , serwera Comet / Web Socket napisanego w Javie. Mimo że jest bardzo wydajny i może nasycić niemal dowolną przepustowość podaną mu w optymalnych warunkach, nadal jest ograniczony do tego, jak szybko można nawiązywać nowe połączenia TCP. To znaczy, jeśli masz dużą rezygnację użytkowników, do której użytkownicy przychodzą i odchodzą bardzo często, wiele połączeń TCP będzie musiało zostać skonfigurowanych / przerwanych. Staramy się łagodzić to utrzymywanie połączeń przy życiu tak długo, jak to możliwe. Ale w końcu wydajność accept () powstrzymuje nasze rdzenie przed obracaniem się i nam się to nie podoba.
Aktualizacja 1
Ktoś opublikował to pytanie w Hacker News , jest tam również kilka pytań / odpowiedzi. Ale postaram się aktualizować to pytanie za pomocą informacji, które znajduję w miarę upływu czasu.
Sprzęt / platformy, na których testowałem to:
- EC2 z typami instancji c1.xlarge (8 rdzeni, 7 GB pamięci RAM) i cc1.4xlarge (2x Intel Xeon X5570, 23 GB pamięci RAM). Stosowanymi AMI były odpowiednio ami-08f40561 i ami-1cad5275. Ktoś zauważył również, że „Grupy bezpieczeństwa” (tj. Zapora sieciowa EC2) również mogą mieć wpływ. Ale w tym scenariuszu testowym próbowałem tylko na localhost, aby wyeliminować takie czynniki zewnętrzne, jak ten. Kolejna plotka, jaką słyszałem, to że instancje EC2 nie mogą zepchnąć więcej niż 100k PPS.
- Dwa prywatne zwirtualizowane serwery z systemem Xen. Jeden miał zero obciążenia przed testem, ale nie zrobił różnicy.
- Prywatny dedykowany serwer Xen w Rackspace. O tych samych wynikach.
Jestem w trakcie ponownego uruchamiania tych testów i wypełniania raportów na https://gist.github.com/985475 Jeśli chcesz pomóc, podaj swoje liczby. To jest łatwe!
(Plan działania został przeniesiony do osobnej, skonsolidowanej odpowiedzi)
źródło
Odpowiedzi:
W tej chwili: Wydajność małych pakietów jest do kitu pod Xen
(zamiast tego przeniesiono z samego pytania do osobnej odpowiedzi)
Według użytkownika HN (programisty KVM?) Wynika to z wydajności małych pakietów w Xen, a także KVM. Jest to znany problem z wirtualizacją i według niego VMX ESX radzi sobie z tym znacznie lepiej. Zauważył również, że KVM wprowadza nowe funkcje zaprojektowane w celu złagodzenia tego ( oryginalny post ).
Te informacje są nieco zniechęcające, jeśli są poprawne. Tak czy inaczej, spróbuję wykonać poniższe kroki, dopóki jakiś guru Xen nie otrzyma ostatecznej odpowiedzi :)
Iain Kay z listy mailingowej użytkowników Xen skompilował ten wykres: Zwróć uwagę na słupki TCP_CRR, porównaj „2.6.18-239.9.1.el5” z „2.6.39 (z Xen 4.1.0)”.
Aktualny plan działania oparty na odpowiedziach / odpowiedziach tutaj i od HN :
Prześlij ten problem do listy mailingowej specyficznej dla Xen i do bugzilli xensource zgodnie z sugestią syneticon-dj. Wiadomość została wysłana na listę użytkownikówXen woczekiwaniu na odpowiedź.Utwórz prosty przypadek testowy na poziomie aplikacji i opublikuj go.Serwer testowy z instrukcjami został utworzony i opublikowany w GitHub . Dzięki temu powinieneś zobaczyć bardziej realistyczny przypadek użycia niż netperf.
Wypróbuj 32-bitową instancję gościa PV Xen, ponieważ 64-bit może powodować większe obciążenie w Xen. Ktoś wspomniał o tym w HN.Nie zrobiło różnicy.Spróbuj włączyć net.ipv4.tcp_syncookies w sysctl.conf, jak sugeruje abofh na HN. To najwyraźniej może poprawić wydajność, ponieważ uścisk dłoni miałby miejsce w jądrze.Nie miałem z tym szczęścia.Zwiększ zaległości z 1024 do czegoś znacznie wyższego, sugerowanego również przez abofh na HN. Może to również pomóc, ponieważ gość może potencjalnie zaakceptować () więcej połączeń podczas wykonywania wycinka podanego przez dom0 (host).
Dokładnie sprawdź, czy conntrack jest wyłączony na wszystkich komputerach, ponieważ może zmniejszyć o połowę szybkość akceptacji (sugerowane przez deubeulyou).Tak, był wyłączony we wszystkich testach.Sprawdź „przepełnienie kolejki nasłuchu i przepełnienie segmentów synchronizacji pamięci w netstat -s” (sugerowane przez mike_esspe na HN).
Podziel obsługę przerwań na wiele rdzeni (RPS / RFS, które próbowałem wcześniej włączyć, powinny to zrobić, ale warto spróbować ponownie). Sugerowane przez adamt z HN.
Wyłączanie odciążania segmentacji TCP i przyspieszania rozproszenia / gromadzenia, jak sugeruje Matt Bailey. (Niemożliwe na EC2 lub podobnych hostach VPS)
źródło
Anegdotycznie stwierdziłem, że wyłączenie akceleracji sprzętowej karty sieciowej znacznie poprawia wydajność sieci na kontrolerze Xen (dotyczy to również LXC):
Scatter-gather accell:
/usr/sbin/ethtool -K br0 sg off
Odciążenie segmentacji TCP:
/usr/sbin/ethtool -K br0 tso off
Gdzie br0 jest mostem lub urządzeniem sieciowym na hoście hiperwizora. Musisz to ustawić, aby wyłączało się przy każdym uruchomieniu. YMMV.
źródło
Może mógłbyś trochę wyjaśnić - czy uruchomiłeś testy pod Xenem na własnym serwerze, czy tylko na instancji EC2?
Zaakceptuj to tylko kolejne wywołanie systemowe, a nowe połączenia różnią się tylko tym, że kilka pierwszych pakietów będzie miało określone flagi - hypervisor, taki jak Xen, na pewno nie zobaczy żadnej różnicy. Inne części twojej konfiguracji mogą: na przykład w EC2 nie byłbym zaskoczony, gdyby Grupy Bezpieczeństwa miały z tym coś wspólnego; Zgłoszono również, że conntrack obniża o połowę liczbę nowych połączeń akceptowanych (PDF) .
Wreszcie, wydaje się, że istnieją kombinacje procesora / jądra, które powodują dziwne użycie procesora / zawieszanie się na EC2 (i prawdopodobnie ogólnie Xen), o czym ostatnio pisał blog Librato .
źródło
Upewnij się, że wyłączyłeś iptables i inne haki w kodzie mostkowym w dom0. Oczywiście dotyczy to tylko konfiguracji Xen w sieci mostowej.
Zależy to od wielkości serwera, ale od mniejszych (procesor 4-rdzeniowy) dedykuj jeden rdzeń procesora Xen dom0 i przypnij go. Opcje uruchamiania hiperwizora:
Czy próbowałeś przekazać fizyczne urządzenie PCI Ethernet do domU? Powinno być dobre zwiększenie wydajności.
źródło