Дуже низька пропускна здатність TCP OpenVPN (100Mbit порт, низьке використання процесора)


27

У мене надзвичайно повільні швидкості передачі OpenVPN між двома серверами. Для цього питання я зателефоную на сервери Server A і Server B.

І сервер A, і сервер B працюють під управлінням CentOS 6.6. Обидва розміщені в центрах обробки даних лінією 100 Мбіт, а передача даних між двома серверами поза OpenVPN працює близько ~ 88 Мбіт / с.

Однак, коли я намагаюся перенести будь-які файли через з'єднання OpenVPN, яке я встановив між сервером A і сервером B, я отримую пропускну здатність близько 6,5 Мбіт / с.

Результати тестування від iperf:

[  4] local 10.0.0.1 port 5001 connected with 10.0.0.2 port 49184
[  4]  0.0-10.0 sec  7.38 MBytes  6.19 Mbits/sec
[  4]  0.0-10.5 sec  7.75 MBytes  6.21 Mbits/sec
[  5] local 10.0.0.1 port 5001 connected with 10.0.0.2 port 49185
[  5]  0.0-10.0 sec  7.40 MBytes  6.21 Mbits/sec
[  5]  0.0-10.4 sec  7.75 MBytes  6.26 Mbits/sec

Окрім цих тестів OpenVPN iperf, обидва сервери практично повністю не працюють з нульовим навантаженням.

Серверу A присвоюється IP 10.0.0.1 і це сервер OpenVPN. Сервер B присвоює IP 10.0.0.2 і це клієнт OpenVPN.

Конфігурація OpenVPN для сервера A така:

port 1194
proto tcp-server
dev tun0
ifconfig 10.0.0.1 10.0.0.2
secret static.key
comp-lzo
verb 3

Конфігурація OpenVPN для сервера B така:

port 1194
proto tcp-client
dev tun0
remote 204.11.60.69
ifconfig 10.0.0.2 10.0.0.1
secret static.key
comp-lzo
verb 3

Що я помітив:

1. Першою моєю думкою було те, що я обмежував вузький процесор на сервері. OpenVPN є однопотоковою, і обидва ці сервери працюють з процесорами Intel Xeon L5520, які не найшвидші. Однак я запустив topкоманду під час одного з тестів iperf і натиснув 1для перегляду використання процесора ядром і виявив, що завантаження процесора було дуже низьким для кожного ядра:

top - 14:32:51 up 13:56,  2 users,  load average: 0.22, 0.08, 0.06
Tasks: 257 total,   1 running, 256 sleeping,   0 stopped,   0 zombie
Cpu0  :  2.4%us,  1.4%sy,  0.0%ni, 94.8%id,  0.3%wa,  0.0%hi,  1.0%si,  0.0%st
Cpu1  :  0.0%us,  0.0%sy,  0.0%ni,100.0%id,  0.0%wa,  0.0%hi,  0.0%si,  0.0%st
Cpu2  :  0.0%us,  0.0%sy,  0.0%ni, 99.7%id,  0.0%wa,  0.0%hi,  0.0%si,  0.3%st
Cpu3  :  0.3%us,  0.0%sy,  0.0%ni, 99.7%id,  0.0%wa,  0.0%hi,  0.0%si,  0.0%st
Cpu4  :  0.0%us,  0.0%sy,  0.0%ni,100.0%id,  0.0%wa,  0.0%hi,  0.0%si,  0.0%st
Cpu5  :  0.0%us,  0.0%sy,  0.0%ni,100.0%id,  0.0%wa,  0.0%hi,  0.0%si,  0.0%st
Cpu6  :  0.0%us,  0.0%sy,  0.0%ni,100.0%id,  0.0%wa,  0.0%hi,  0.0%si,  0.0%st
Cpu7  :  0.0%us,  0.0%sy,  0.0%ni,100.0%id,  0.0%wa,  0.0%hi,  0.0%si,  0.0%st
Cpu8  :  0.0%us,  0.0%sy,  0.0%ni,100.0%id,  0.0%wa,  0.0%hi,  0.0%si,  0.0%st
Cpu9  :  0.0%us,  0.0%sy,  0.0%ni,100.0%id,  0.0%wa,  0.0%hi,  0.0%si,  0.0%st
Cpu10 :  0.0%us,  0.0%sy,  0.0%ni,100.0%id,  0.0%wa,  0.0%hi,  0.0%si,  0.0%st
Cpu11 :  0.0%us,  0.0%sy,  0.0%ni,100.0%id,  0.0%wa,  0.0%hi,  0.0%si,  0.0%st
Cpu12 :  0.0%us,  0.0%sy,  0.0%ni,100.0%id,  0.0%wa,  0.0%hi,  0.0%si,  0.0%st
Cpu13 :  0.0%us,  0.0%sy,  0.0%ni,100.0%id,  0.0%wa,  0.0%hi,  0.0%si,  0.0%st
Cpu14 :  0.0%us,  0.0%sy,  0.0%ni,100.0%id,  0.0%wa,  0.0%hi,  0.0%si,  0.0%st
Cpu15 :  0.0%us,  0.0%sy,  0.0%ni,100.0%id,  0.0%wa,  0.0%hi,  0.0%si,  0.0%st
Mem:    946768k total,   633640k used,   313128k free,    68168k buffers
Swap:  4192188k total,        0k used,  4192188k free,   361572k cached

2. Час Ping значно збільшується в тунелі OpenVPN, поки працює iperf. Якщо iperf не працює, частота пінг-проходу через тунель постійно становить 60 мс (нормально). Але коли iperf працює і штовхає великі затори, пінг-часи стають нестабільними. Нижче ви можете бачити, наскільки стабільні періоди ping до 4-го ping, коли я розпочав тест iperf:

PING 10.0.0.2 (10.0.0.2) 56(84) bytes of data.
64 bytes from 10.0.0.2: icmp_seq=1 ttl=64 time=60.1 ms
64 bytes from 10.0.0.2: icmp_seq=2 ttl=64 time=60.1 ms
64 bytes from 10.0.0.2: icmp_seq=3 ttl=64 time=60.2 ms
** iperf test begins **
64 bytes from 10.0.0.2: icmp_seq=4 ttl=64 time=146 ms
64 bytes from 10.0.0.2: icmp_seq=5 ttl=64 time=114 ms
64 bytes from 10.0.0.2: icmp_seq=6 ttl=64 time=85.6 ms
64 bytes from 10.0.0.2: icmp_seq=7 ttl=64 time=176 ms
64 bytes from 10.0.0.2: icmp_seq=8 ttl=64 time=204 ms
64 bytes from 10.0.0.2: icmp_seq=9 ttl=64 time=231 ms
64 bytes from 10.0.0.2: icmp_seq=10 ttl=64 time=197 ms
64 bytes from 10.0.0.2: icmp_seq=11 ttl=64 time=233 ms
64 bytes from 10.0.0.2: icmp_seq=12 ttl=64 time=152 ms
64 bytes from 10.0.0.2: icmp_seq=13 ttl=64 time=216 ms

3. Як було сказано вище, я пробіг iperf поза тунелем OpenVPN, і пропускна здатність була нормальною - ~ 88Mbps послідовно.

Що я спробував:

1. Я думав, що стиснення може зіпсувати речі, тому я вимкнув стиснення, видаливши comp-lzoз обох конфігурацій і перезапустивши OpenVPN. Поліпшення немає.

2. Незважаючи на те, що раніше я виявив, що використання процесора низьке, я вважав, що шифр за замовчуванням може бути трохи надто інтенсивним для того, щоб система не відставала. Тому я додав cipher RC2-40-CBCдо обох конфігурацій (дуже легкий шифр) і перезапустив OpenVPN. Поліпшення немає.

3. Я читав на різних форумах про те, як налаштування фрагмента, mssfix та mtu-tun може допомогти в продуктивності. Я грав з декількома варіаціями, як описано в цій статті , але знову ж таки, без покращення.

Будь-які ідеї щодо того, що може спричинити такі низькі показники OpenVPN?


Чи допомагають будь-які посилання, коментарі звідси? forums.openvpn.net/topic10593.html
Метт

Більшість пропозицій є речі, які я вже спробував: 1. перевірити наявність вузького місця у процесорі, 2. перевірити швидкість передачі даних без VPN, 3. стиснути перемикання, 4. вибрати швидший шифр тощо. Не пощастить жодному з них ще: - / Це химерно. Окрім повільної швидкості та високих / мінливих часів пінг, я не бачу інших вказівок, де може бути вузьке місце.
Елліот Б.

Чи обидві машини в одному центрі обробки даних? 60 мс у тому ж центрі обробки даних досить високий. Мені може спастися спробувати, cipher noneхоча я сумніваюся, що це допоможе.
Зоредаче

@Zoredache Вибачте - мені не було зрозуміло розташування серверів - сервер A знаходиться у Далласі, а сервер B - у Сіетлі.
Елліот Б.

Ви перевірили MTU? Esp: параметри tun-mtu, фрагмента та mssfix? Документація
Ленні

Відповіді:


26

Після багатьох перетворень файлів Google і конфігурації я знайшов рішення. Зараз я отримую стійкі швидкості 60Mbps і розриваюся до 80Mbps. Це трохи повільніше, ніж швидкість передачі, яку я отримую за межами VPN, але я думаю, що це так добре, як і отримає.

Першим кроком було встановлення sndbuf 0та rcvbuf 0налаштування OpenVPN як для сервера, так і для клієнта.

Я вніс цю зміну, побачивши пропозицію зробити це на публічному форумі (який є англійською мовою перекладу російської оригінальної публікації ), який я цитую тут:

Це липень 2004 р. Звичайна швидкість домашнього Інтернету в розвинених країнах становить 256-1024 Кбіт / с, у менш розвинених країнах - 56 Кбіт / с. Linux 2.6.7 був випущений недавно, а 2.6.8, де TCP Windows масштабування розміру Windows буде включено за замовчуванням, виходить лише через місяць. OpenVPN активно розвивається вже 3 роки, версія 2.0 майже виходить. Один з розробників вирішує додати якийсь код для буфера сокета, я думаю, щоб уніфікувати розміри буфера між ОС. У Windows щось не в порядку з MTU адаптерів, якщо встановлені спеціальні розміри буферів, тож, нарешті, він перетворюється на наступний код:

#ifndef WIN32
o->rcvbuf = 65536;
o->sndbuf = 65536;
#endif

Якщо ви використовували OpenVPN, ви повинні знати, що він може працювати над TCP та UDP. Якщо встановити спеціальне значення буфера TCP для сокетів на рівні 64 КБ, алгоритм масштабування розміру вікна TCP не може налаштувати розмір вікна більше 64 КБ. Що це означає? Це означає, що якщо ви підключаєтесь до іншого VPN-сайту через довге жирове посилання, тобто США до Росії з пінг-інтервалом близько 100 мс, ви не зможете отримати швидкість більше 5,12 Мбіт / с із налаштуваннями буфера OpenVPN за замовчуванням. Вам потрібно щонайменше 640 КБ буфера, щоб отримати 50 Мбіт / с через це посилання. UDP буде працювати швидше, оскільки він не має розміру вікна, але також не буде працювати дуже швидко.

Як ви вже здогадалися, в останньому випуску OpenVPN все ще використовується розмір буфера розетки 64 Кб. Як нам вирішити це питання? Найкращий спосіб - заборонити OpenVPN встановлювати власні розміри буфера. Ви повинні додати такий код у файлах конфігурації сервера та клієнта:

sndbuf 0
rcvbuf 0

Автор далі описує, як підштовхнути коригування розміру буфера до клієнта, якщо ви самі не контролюєте налаштування клієнта.

Після того, як я внесла ці зміни, швидкість пропускної здатності зросла до 20 Мбіт / с. Потім я побачив, що використання центрального процесора було трохи вище в одному ядрі, тому я видалив comp-lzo(стиснення) з конфігурації як на клієнті, так і на сервері. Еврика! Швидкість передачі стрибнула до 60 Мбіт / с, і 80 Мбіт / с.

Я сподіваюся, що це допоможе комусь іншому вирішити власні проблеми з повільністю OpenVPN!


4

Після кількох спроб я досяг хорошого рішення. У моєму випадку відповідь @ Елліот не допомогла. Подивившись більше, я знайшов цей фрагмент, який потрібно додати в конфігурацію сервера, який зробив цю роботу

sndbuf 393216
rcvbuf 393216
push "sndbuf 393216"
push "rcvbuf 393216"

У мене невеликий сервер OpenVPN, який працює на Raspberry PI3, і тепер я отримую 71 Мбіт / с низхідній лінії зв'язку та 16 Мбіт / с . Завантаження обмежене, оскільки потужність процесора. Зараз моя конфігурація така:

client-to-client
duplicate-cn
keepalive 10 120
cipher AES-128-CBC
#cipher AES-256-CBC <<<---- lowers the speed to around 50Mbps, still not bad
comp-lzo
user nobody
group nogroup
persist-key
persist-tun
tun-mtu 9000

OpenVPN 2.4.0 arm-unknown-linux-gnueabihf з OpenSSL 1.0.2l

Це настільки дивно, що така проблема щодо конфігурації буфера за замовчуванням все ще існує.

[EDIT] Мій файл client.ovpn структурований так:

client
dev tun
proto tcp
remote SERVER.IP.ADDRESS.HERE
resolv-retry infinite
nobind
persist-key
persist-tun
mute-replay-warnings
ns-cert-type server
tun-mtu 9000
key-direction 1
cipher AES-128-CBC
comp-lzo
verb 1
mute 20
<ca>
-----BEGIN CERTIFICATE-----
[...]
-----END CERTIFICATE-----
</ca>
<cert>
-----BEGIN CERTIFICATE-----
[...]
-----END CERTIFICATE-----
</cert>
<key>
-----BEGIN RSA PRIVATE KEY-----
[...]
-----END RSA PRIVATE KEY-----
</key>
<tls-auth>
-----BEGIN OpenVPN Static key V1-----
[...]
-----END OpenVPN Static key V1-----
</tls-auth>

Налаштування розмірів буфера допомогло мені.
Рольф

що ви помістили у файл .ovpn клієнта?
Патоші パ ト シ

@Patoshi パ ト シ Я прокоментував sndbuf та recbuf, поставив відповідні шифри та стиснення та залишив параметри за замовчуванням.
Ядро

@Kernel чи можете ви показати мені, що у вас є у клієнта? Я роблю OpenVPN-з'єднання з Гонконгу до Нью-Йорка, і його випадково повільно, а іноді і відключається. Я не впевнений, чому.
Патоші パ ト シ

@Patoshi パ ト シ Я відредагував свою відповідь, перевір її ще раз. Тим не менш, я б запропонував вам скористатися UDP, оскільки це може допомогти вам вирішити проблему нестабільного зв’язку з вашим сервером. Дійсно, це лише припущення, я ніколи не намагався порівняти це рішення в цій ситуації.
Ядро

1

Відповідно до Config's, ви використовуєте TCP як транспорт для тунелю. Подумайте про використання UDP замість TCP, оскільки намет з накопиченими TCP-з'єднаннями створює проблеми в ситуаціях втрати пакетів.

Як довідку див. Чому TCP Over TCP - погана ідея


На жаль, UDP не є для нас варіантом. Нам потрібно переконатися, що пакети даних, які ми передаємо, надходять як очікувалося. Тим не менш, ми раніше експериментували з UDP, і низька швидкість передачі була все ще проблемою.
Елліот Б.

6
We need to ensure that the data packets we transmit arrive as expected.і чи не так обробляється протокол, який тунелюється? Чому, на вашу думку, ваш тунель повинен бути тією дією, яка це примушує?
Зоредаче

Це, мабуть, так, але ми використовуємо OpenVPN для далекої асинхронної реалізації DRBD (тобто реплікації файлової системи). Цілісність даних дійсно важлива, тому, хоча DRBD, ймовірно, має внутрішні механізми для перевірки цілісності передачі, я б краще зберігати його на TCP. Так чи інакше, коли ми мали це на UDP, у нас все ще була низька пропускна здатність.
Елліот Б.

3
@ElliotB. Оскільки DRBD сам використовує TCP для реплікації, він буде повторно переданий у випадку втрати пакету UDP OpenVPN. Насправді, використовуючи TCP в цьому випадку, ви зробите два ретрансфери замість одного ... один з яких буде викинутий. І ви, можливо, створюєте досить довге вікно без трафіку DRBD (через це навіть отримаєте зламану реплікацію). Як тільки ви отримаєте якийсь пакет пакетів на маршруті, ви побачите, як це погано мислити.
Фокс

@Fox Дякую за надання роз'яснень! Дійсно, DRBD використовує TCP (drbd.linbit.com/users-guide/s-prepare-network.html). Раніше пропозиція Lairsdragon про перехід на UDP не була актуальною, оскільки UDP також відчував надзвичайно низькі швидкості передачі, але, оскільки впроваджував рішення, яке я розмістив вище, ми зробили перехід на UDP і отримали ще одне збільшення продуктивності на кілька Мбіт / с.
Елліот Б.

1

У нас є два міжконтинентальні сервери, які зв’язуються один з одним, швидкість між ними коливається близько 220 Мбіт / с.

Всередині (UDP) OpenVPN тунелю швидкість буде в середньому на 21 Мбіт / с - приблизно в 10 разів повільніше.

(Існує значна затримка між серверами: близько 130 мс, а передачі вимірювалися за допомогою Iperf3 в режимі TCP.)

Спробував усі пропозиції щодо відповідей, що стосуються цього написання, і нічого не допомогло.

Єдине, що нарешті допомогло, було це трохи:

--txqueuelen 4000

Відповідно до посібника з OpenVPN:

–txqueuelen n 
(Linux only) Set the TX queue length on the TUN/TAP interface. Currently defaults to 100.

Встановивши цей параметр на сервері та клієнті, я зміг досягти тих же швидкостей «прямого зв’язку» (~ 250 Мбіт / с) також під тунелем OpenVPN.

Я вже використовував rcvbuf 0і sndbuf 0, хоча б поодинці , вони зовсім не допомагали.

Я знайшов ці рекомендації в обох: цій сторінці на форумах OpenVPN , а також на цій сторінці у вікі UDPspeeder .

Ще одна примітка: мені вдалося досягти більшої швидкості, використовуючи передачі UDP в iperf, але це також спричинило б досить високі втрати пакету.

Якщо якимось випадком вам потрібно використовувати VPN, щоб тунелювати два місця з втратними посиланнями, я б радив розглянути можливість використання якогось тунелю Forward-Error-Correction (FEC) під самим VPN. Два, з якими мені вдалося знайти і з якими працювати:

  • Вищезгаданий UDPspeeder , який тунелює з'єднання UDP;
  • kcptun , який тунелює з'єднання TCP;

Обидва можуть багато допомогти з пакетними втратами (в першу чергу витрачаючи більше пропускної здатності), і, в кінцевому рахунку, навіть приводять до збільшення пропускної здатності даних, навіть із доданими накладними витратами, що справді акуратно, якщо ви запитаєте мене.

(Це тому, що втрата пакетів може дійсно зіпсувати мережу , особливо TCP . Див. Сторінку 6.)

Я б вважав за краще використовувати OpenVPN на UDP з усіх звичних причин, але мені складно боротися з UDPspeeder, коли у вас обоє затримки більше 100 мс і> 10 Мбіт / с.

kcptun, однак, чудово працював із дуже невеликим налаштуванням, і насправді дуже збільшив пропускну здатність наших серверів один з одним. =)

У розширеній примітці тут ви можете знайти більш детальні пояснення щодо налаштування деяких частин продуктивності OpenVPN.


0

Для мене у мене був сервер VPS з налаштуванням сервера openvpn в Японії, і для мого клієнтського підключення використовувався DDWRT в режимі клієнта OpenVPN в Нью-Йорку. Я отримував лише 1-2 Мбіт / с на 100 Мбіт з'єднання. Найкраще, що мені вдалося оптимізувати, це було 5 Мбіт / с, що було достатньо для того, що мені потрібно, і настільки ж оптимізованого, як я можу зробити так, що я вірю.

Мої налаштування сервера OpenVPN:

tun-mtu 9000
sndbuf 393216
rcvbuf 393216
push "sndbuf 393216"
push "rcvbuf 393216"
comp-lzo
txqueuelen 4000
######
port 10111
proto udp
dev tun
user nobody
group nobody
persist-key
persist-tun
keepalive 10 120
topology subnet
server x.x.0.0 255.255.255.0
ifconfig-pool-persist ipp.txt
push "dhcp-option DNS 1.0.0.1"
push "dhcp-option DNS 1.1.1.1"
push "redirect-gateway def1 bypass-dhcp"
dh none
ecdh-curve prime256v1
#tls-crypt tls-crypt.key 0
crl-verify crl.pem
ca ca.crt
cert server_IzA1QdFzHLRFfEoQ.crt
key server_IzA1QdFzHLRFfEoQ.key
auth SHA256
#cipher AES-128-GCM
#cipher AES-128-CBC
#ncp-ciphers AES-128-GCM
#ncp-ciphers AES-128-CBC
#tls-server
#tls-version-min 1.2
#tls-cipher TLS-ECDHE-ECDSA-WITH-AES-128-GCM-SHA256
#tls-cipher TLS-DHE-RSA-WITH-AES-128-CBC-SHA
status /var/log/openvpn/status.log
verb 3

Мої налаштування клієнта DDWRT OpenVPN також помічені на екрані екрана:

tun-mtu 9000
comp-lzo
##########
resolv-retry infinite
nobind
persist-key
persist-tun
remote-cert-tls server
verify-x509-name server_IzA1QdFzHLRFfEoQ name
auth SHA256
auth-nocache
setenv opt block-outside-dns # Prevent Windows 10 DNS leak
verb 3

введіть тут опис зображення

введіть тут опис зображення

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.