Відповіді:
Основний TCP ACK говорить: "Я отримав усі байти до X." Вибірковий ACK дозволяє сказати "Я отримав байти XY і VZ".
Так, наприклад, якщо хост надіслав вам 10 000 байт, а 3000 -5000 байтів були втрачені під час транзиту, ACK сказав: "Я все отримав до 3000". На інший кінець знову доведеться надсилати байти 3001-10000. SACK міг би сказати: "Я отримав 1000-2999 і 5001-10000", і хост просто відправить 3000-5000.
Це чудово через високу пропускну здатність, втрату (або велику затримку). Проблема полягає в тому, що це може спричинити серйозні проблеми в роботі за конкретних обставин. Звичайні TCP ACK змусять сервер обробляти високопропускну здатність, втрату зв'язку з дитячими рукавичками (надсилати 500 байт, чекати, надсилати 500 байтів, чекати тощо). SACK дозволяє адаптуватися до великої затримки, оскільки він точно знає, скільки пакетів насправді було втрачено.
Ось де можуть статися погані речі. Зловмисник може змусити ваш сервер тривалий час зберігати велику чергу повторної передачі, а потім обробляти всю цю прокляту річ знову і знову. Це може прив’язати процесор, з’їсти оперативну пам’ять і споживати більше пропускної здатності, ніж слід. У двох словах, легка система може ініціювати DoS проти сервера BEfier.
Якщо ваш сервер надійний і не обслуговує великі файли, ви досить добре захищені від цього.
Якщо ви здебільшого обслуговуєте інтранет або іншу групу користувачів із низькою затримкою, SACK нічого не купує і може бути вимкнено з міркувань безпеки без втрати продуктивності.
Якщо ви перебуваєте на низькосмуговій лінії зв'язку (скажімо, 1 Мбіт / с або менше як абсолютно довільне правило), SACK може спричинити проблеми в звичайних операціях, насичуючи ваше з'єднання, і його слід вимкнути.
Зрештою, це залежить від вас. Поміркуйте, що ви обслуговуєте, кому, з чого, і зважте ступінь свого ризику на ефективність SACK.
Тут чудовий огляд SACK та його вразливості .
Ще однією причиною того, що TCP SACK часто відключається, є те, що там є дивовижна кількість мережевих передач, які не вдається правильно обробити цю опцію. Ми постійно бачимо це за допомогою високошвидкісного продукту передачі файлів, який ми надаємо та використовує TCP. Найпоширеніша проблема - це пристрої шлюзу, які роблять такі випадки, як рандомізація послідовних номерів для пакетів TCP, які переходять через пристрій від внутрішніх мереж до зовнішніх, але не "не випадкову" вибір параметрів TCP SACK, які можуть бути надіслані з віддаленого пристрою кінець. Якщо фактичні значення SACK не будуть переведені на відповідні значення цими пристроями, тоді сеанс TCP ніколи не завершиться в умовах втрати пакету, коли віддалений кінець намагається використовувати SACK для отримання селективних переваг ACK.
Ймовірно, це буде меншою проблемою, якби люди стали більш агресивно застосовувати профілактичне обслуговування програмного забезпечення до цього обладнання, але вони цього не прагнуть.
Я можу підтвердити з гіркого досвіду, що tcp_sack = 1 спричиняє затримку передачі даних через sftp / rsync / scp тощо з файлами, що перевищують близько 12 Мб, при використанні певних пристроїв брандмауера Cisco ASA.
КОЖНИЙ час це затримається.
Ми передавали спеціальний зв'язок на 100 Мбіт / с між хостом A і хостом B у двох різних центрах обробки даних, обидва використовували брандмауер cisco та апаратне перемикання з центрами.
Це можна дещо пом'якшити, змінивши розміри буфера - наприклад, я не зміг перенести файл 1 ГБ через sftp з хоста А на хост В, якщо я не встановив буфер sftp на 2048, але я міг би незалежно, чи хостинг B перетягував файл з А.
Експерименти з тим самим файлом, що використовує налаштування буфера rsync та надіслати / приймати, дозволили мені отримати близько 70 Мб файлу 1 ГБ, висунутого від А до В.
Однак остаточною відповіддю було відключити tcp_sack на хості A. Спочатку встановивши tcp_sack = 0 в ядрі на ходу, але в кінцевому підсумку - я додав його до свого /etc/sysctl.conf