"За
<br />
TCP MSS (Maximum Segment Size) — максимальный размер полезной нагрузки одного TCP-сегмента. Формула: MSS = MTU — 40 байт. При PPPoE, VPN-туннелях и любой инкапсуляции MTU уменьшается. Если MSS не подстроен, а ICMP заблокирован провайдером, HTTPS-сессии зависают на TLS-рукопожатии. Решение: MSS Clamping — одно правило в mangle на <a class="wpil_keyword_link" href="https://it-apteka.com/tag/mikrotik/" target="_blank" rel="noopener" title="mikrotik" data-wpil-keyword-link="linked" data-wpil-monitor-id="2109">MikroTik</a> или один параметр в настройках Keenetic.<br />
<h2>Диагноз: HTTPS виснет, HTTP летит, вы уже всё перепробовали</h2>
<p>HTTP работает. HTTPS крутит колесо и выдаёт тайм-аут. VPN поднят, пинги идут, а корпоративный портал на TLS не открывается. PPPoE подключили — лёгкие сайты летят, тяжёлые страницы зависают.</p>
<p>Это не браузер, не сертификат и не <a class="wpil_keyword_link" href="https://it-apteka.com/tag/dns/" target="_blank" rel="noopener" title="DNS" data-wpil-keyword-link="linked" data-wpil-monitor-id="2107">DNS</a>. В девяти случаях из десяти — неправильный MSS. Разберём, что это такое, почему ломает именно HTTPS, и закроем проблему командами для MikroTik и Keenetic.</p>
<p>Что получишь после прочтения:</p>
<ul>
<li>Понимание механизма MSS и его связи с MTU</li>
<li>Готовые команды MikroTik (RouterOS 6.x и 7.x) и Keenetic</li>
<li>Инструменты <a href="https://it-apteka.com/troubleshooting-setevyh-problem-15-komand-dlja-diagnostiki-v-windows-i-linux/" title="Troubleshooting сетевых проблем: 15 команд для диагностики в Windows и Linux" target="_blank" rel="noopener" data-wpil-monitor-id="2466">диагностики — найдёшь проблему</a> до того как что-то менять</li>
<li>Troubleshooting типичных ошибок при настройке MSS Clamping</li>
<li>IPv6 — отдельный блок, потому что про него всегда забывают</li>
<li>FAQ под реальные вопросы из поиска</li>
</ul>
<p>Время на настройку: 5-10 минут. Время на диагностику: 15-20 минут если проблема нестандартная.</p>
<h2>Что такое MSS (Maximum Segment Size) и как он связан с MTU</h2>
<p><strong>MSS — это максимальный размер полезной нагрузки одного TCP-сегмента</strong> без учёта заголовков IP и TCP. Проще говоря: сколько байт данных влезает в один пакет на уровне TCP.</p>
<p>MSS неразрывно связан с MTU (Maximum Transmission Unit) — максимальным размером кадра на уровне канала передачи данных. Связь прямая:</p>
<pre><code class="language-bash">
# Формула расчёта MSS:
MSS = MTU - 20 (IP header) - 20 (TCP header)
MSS = MTU - 40
# Пример для стандартного Ethernet:
MSS = 1500 - 40 = 1460
# Пример для PPPoE:
# PPPoE добавляет 8 байт заголовка, поэтому MTU = 1492
MSS = 1492 - 40 = 1452
</code></pre>
<p>MSS анонсируется в момент TCP-рукопожатия — в пакете SYN. Каждая из сторон сообщает, какой максимальный сегмент она готова принять. Дальше соединение работает с наименьшим из двух значений.</p>
<h3>Значения MSS для популярных типов соединений</h3>
<table>
<thead>
<tr>
<th>Тип соединения</th>
<th>MTU</th>
<th>Overhead</th>
<th>MSS</th>
<th>Примечание</th>
</tr>
</thead>
<tbody>
<tr>
<td>Ethernet (стандарт)</td>
<td>1500</td>
<td>40</td>
<td>1460</td>
<td>Базовое значение</td>
</tr>
<tr>
<td>PPPoE (DSL/GPON)</td>
<td>1492</td>
<td>40</td>
<td>1452</td>
<td>PPPoE = 8 байт overhead</td>
</tr>
<tr>
<td>L2TP без шифрования</td>
<td>1460</td>
<td>40</td>
<td>1420</td>
<td>L2TP header ~40 байт</td>
</tr>
<tr>
<td>L2TP + IPsec</td>
<td>1418</td>
<td>40</td>
<td>1378</td>
<td>IPsec ESP добавляет ~50 байт</td>
</tr>
<tr>
<td>IPsec (ESP, AES-256)</td>
<td>1418</td>
<td>40</td>
<td>1378</td>
<td>Зависит от cipher suite</td>
</tr>
<tr>
<td>GRE-туннель</td>
<td>1476</td>
<td>40</td>
<td>1436</td>
<td>GRE header = 24 байта</td>
</tr>
<tr>
<td>WireGuard VPN</td>
<td>1420</td>
<td>40</td>
<td>1380</td>
<td>WireGuard overhead ~80 байт</td>
</tr>
<tr>
<td>OpenVPN (UDP)</td>
<td>~1400</td>
<td>40</td>
<td>~1360</td>
<td>Зависит от cipher и компрессии</td>
</tr>
<tr>
<td>GRE поверх PPPoE</td>
<td>1468</td>
<td>40</td>
<td>1428</td>
<td>Складываем overhead оба уровня</td>
</tr>
</tbody>
</table>
<h3>Архитектура: как MSS анонсируется в TCP-рукопожатии</h3>
<pre class="mermaid">
%%{init: {
'theme': 'base',
'themeVariables': {
'primaryColor': '#f8fafc',
'primaryTextColor': '#1e293b',
'primaryBorderColor': '#94a3b8',
'noteBkgColor': '#fefce8',
'noteTextColor': '#713f12',
'noteBorderColor': '#fbbf24',
'actorBkg': '#f8fafc',
'actorBorder': '#94a3b8',
'actorTextColor': '#1e293b',
'fontSize': '15px',
'fontFamily': 'ui-sans-serif, system-ui, sans-serif'
},
'sequence': {
'mirrorActors': false,
'messageAlign': 'center',
'actorMargin': 100,
'width': 160,
'noteMargin': 12
}
}}%%
sequenceDiagram
participant C as Клиент (MSS 1460)
participant R as Роутер PPPoE
participant S as Сервер (MSS 1460)
C->>R: SYN, MSS=1460
Note over R: MSS Clamping: 1460 -> 1452
R->>S: SYN, MSS=1452
S->>R: SYN-ACK, MSS=1452
R->>C: SYN-ACK, MSS=1452
C->>S: ACK (сессия открыта, MSS=1452)
Note over C,S: Оба передают сегменты <= 1452 байт
</pre>
<p>Без MSS Clamping клиент анонсирует MSS=1460, сервер соглашается. Но пакеты по пути через PPPoE-интерфейс не влезают в MTU=1492 при размере сегмента 1460+40=1500 байт. Точнее, влезают ровно впритык для IPv4 - но TLS ClientHello с расширениями легко выходит за эти рамки.</p>
<h2>Почему именно HTTPS зависает, а HTTP работает</h2>
<p>Здесь важно понять механизм <strong>Path MTU Discovery (PMTUD)</strong>. Когда пакет не влезает в MTU промежуточного узла, маршрутизатор должен либо фрагментировать его, либо - если установлен флаг DF (Don't Fragment) - отправить назад ICMP Type 3 Code 4 "Fragmentation Needed". Получив это сообщение, отправитель снижает размер сегмента.</p>
<p>Проблема: многие провайдеры и файрволы блокируют ICMP. Полностью. Из-за паранойи, из-за кривой политики безопасности, из-за того что "так было настроено в 2009 году и никто не трогал". В результате отправитель никогда не узнаёт, что пакет не прошёл. Пакеты молча отбрасываются, соединение зависает.</p>
<h3>Почему HTTP страдает меньше</h3>
<p>HTTP-запрос типично мал: GET /, Host, User-Agent - влезает в один пакет хорошо. Ответ сервера разбивается на мелкие сегменты. Если один потерялся - TCP ретрансмиссия, и всё равно доходит.</p>
<p>TLS-рукопожатие устроено иначе. Пакет <strong>ClientHello</strong> в TLS 1.3 содержит:</p>
<ul>
<li>список поддерживаемых cipher suites (десятки вариантов)</li>
<li>список расширений: SNI, ALPN, session tickets, key_share</li>
<li>публичный ключ Diffie-Hellman (32-64 байта)</li>
<li>supported_groups, signature_algorithms</li>
</ul>
<p>Итого ClientHello легко достигает 400-600 байт. Это нормально. Но пакет передаётся с флагом DF=1. Если на пути есть PPPoE или туннель с уменьшенным MTU - и ICMP заблокирован - этот пакет молча дропается. Браузер ждёт ответа, таймаут, retry, снова таймаут.</p>
<h3>Поток данных при заблокированном PMTUD</h3>
<pre class="mermaid">
%%{init: {
'theme': 'base',
'themeVariables': {
'primaryColor': '#ffffff',
'primaryTextColor': '#1e293b',
'primaryBorderColor': '#94a3b8',
'lineColor': '#64748b',
'fontSize': '15px',
'fontFamily': 'ui-sans-serif, system-ui, sans-serif'
},
'flowchart': {'curve': 'linear', 'nodeSpacing': 50, 'rankSpacing': 50}
}}%%
flowchart TD
A["Клиент отправляет TLS ClientHello (DF=1, размер > MTU туннеля)"] --> B["Промежуточный роутер PPPoE/VPN"]
B --> C{"Пакет влезает в MTU?"}
C -->|"Да"| D["Пакет проходит дальше"]
C -->|"Нет"| E{"ICMP разрешён?"}
E -->|"Да (PMTUD работает)"| F["ICMP Fragmentation Needed -> клиент снижает MSS"]
E -->|"Нет (ICMP заблокирован)"| G["Пакет дропается МОЛЧА"]
G --> H["Клиент ждёт ответа - тайм-аут"]
H --> I["Retry - снова тайм-аут"]
I --> J["HTTPS не работает"]
F --> K["HTTPS работает после адаптации"]
D --> K
style G fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#b91c1c
style J fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#b91c1c
style K fill:#f8fafc,stroke:#22c55e,stroke-width:2px,color:#15803d
style F fill:#f8fafc,stroke:#22c55e,stroke-width:2px,color:#15803d
</pre>
<h2>Что такое MSS Clamping и как он решает проблему</h2>
<p><strong>MSS Clamping</strong> - механизм, при котором маршрутизатор на лету изменяет значение MSS в TCP SYN-пакетах, приводя его к безопасному значению для данного канала.</p>
<p>Ключевые особенности:</p>
<ul>
<li><strong>Работает только с SYN и SYN-ACK пакетами</strong> - только при открытии нового TCP-соединения. Установившиеся сессии не затрагиваются.</li>
<li><strong>Не ломает соединение</strong> - уменьшает анонсируемый MSS до допустимого предела.</li>
<li><strong>Решает проблему заблокированного PMTUD</strong> - стороны изначально договариваются на правильный размер сегмента, до первого большого пакета.</li>
<li><strong>Прозрачно для конечных узлов</strong> - <a href="https://it-apteka.com/nastrojka-ntp-na-mikrotik-klient-i-server-shpargalka-dlja-ros-6-i-7/" title="Настройка NTP MikroTik: клиент, сервер и всё что ломается без него" target="_blank" rel="noopener" data-wpil-monitor-id="2551">клиент и сервер</a> не знают, что кто-то подправил их SYN.</li>
</ul>
<h3>Схема работы MSS Clamping</h3>
<pre class="mermaid">
%%{init: {
'theme': 'base',
'themeVariables': {
'primaryColor': '#ffffff',
'primaryTextColor': '#1e293b',
'primaryBorderColor': '#94a3b8',
'lineColor': '#64748b',
'fontSize': '15px',
'fontFamily': 'ui-sans-serif, system-ui, sans-serif'
},
'flowchart': {'curve': 'linear', 'nodeSpacing': 50, 'rankSpacing': 50}
}}%%
flowchart LR
A["Клиент SYN MSS=1460"] --> B["MikroTik Mangle"]
B --> C["change-mss clamp-to-pmtu"]
C --> D["SYN MSS=1452 (PPPoE)"]
D --> E["Сервер принимает"]
style B fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style C fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
</pre>
<h2>Настройка MSS Clamping на MikroTik</h2>
<h3>Системные требования</h3>
<table>
<thead>
<tr>
<th>Компонент</th>
<th>Минимальная версия</th>
<th>Рекомендуется</th>
<th>Примечание</th>
</tr>
</thead>
<tbody>
<tr>
<td>RouterOS</td>
<td>6.40</td>
<td>7.x (LTS)</td>
<td>clamp-to-pmtu доступен с 6.x</td>
</tr>
<tr>
<td>Тип устройства</td>
<td>Любой MikroTik</td>
<td>hEX, RB4011, CCR</td>
<td>Mangle есть на всех</td>
</tr>
<tr>
<td>Права доступа</td>
<td>full или write</td>
<td>full</td>
<td>Нужен доступ к Firewall</td>
</tr>
</tbody>
</table>
<p>На момент публикации актуальна RouterOS 7.18. Перед применением проверь свежие релизы на <a href="https://mikrotik.com/download" target="_blank" rel="noopener noreferrer">mikrotik.com/download</a>.</p>
<h3>Шаг 1 - Проверяем MTU интерфейса</h3>
<p>Прежде чем что-то настраивать, смотрим что есть. Открой Terminal в Winbox или подключись по SSH.</p>
<pre><code class="language-bash">
# Смотрим все интерфейсы и их MTU:
/interface print detail
# Конкретно для PPPoE-подключения:
/interface pppoe-client print detail
# Проверяем MTU через ping с флагом DF:
/tool ping address=8.8.8.8 size=1472 do-not-fragment=yes count=4
# Если ответ есть - MTU 1500, MSS 1460
# Если тайм-аут - уменьшай size до получения ответа
# Бинарный поиск MTU:
/tool ping address=8.8.8.8 size=1452 do-not-fragment=yes count=2
/tool ping address=8.8.8.8 size=1464 do-not-fragment=yes count=2
/tool ping address=8.8.8.8 size=1453 do-not-fragment=yes count=2
</code></pre>
<p>Результат: знаешь реальный MTU канала. Теперь считаем MSS: MTU - 40.</p>
<h3>Шаг 2 - MSS Clamping с автоматической подстройкой (рекомендуется)</h3>
<p>Вариант с <code>clamp-to-pmtu</code> - динамически определяет допустимый MSS по MTU исходящего интерфейса. Не нужно вручную считать и обновлять значение при смене MTU.</p>
<pre><code class="language-bash">
# Основное правило - для транзитного трафика через роутер:
/ip firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
action=change-mss \
new-mss=clamp-to-pmtu \
comment="MSS Clamping IPv4 clamp-to-pmtu"
# Проверяем что правило создалось:
/ip firewall mangle print
</code></pre>
<h3>Шаг 3 - MSS Clamping с фиксированным значением</h3>
<p>Нужен если <code>clamp-to-pmtu</code> не даёт нужного результата или ты точно знаешь значение MTU. Для PPPoE с MTU 1492 MSS = 1452.</p>
<pre><code class="language-bash">
# Фиксированное значение для PPPoE:
/ip firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
action=change-mss \
new-mss=1452 \
comment="MSS Clamping PPPoE fixed 1452"
# Для L2TP/IPsec (MTU ~1418):
/ip firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
action=change-mss \
new-mss=1378 \
comment="MSS Clamping L2TP-IPsec fixed 1378"
# Для WireGuard (MTU 1420):
/ip firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
action=change-mss \
new-mss=1380 \
comment="MSS Clamping WireGuard fixed 1380"
</code></pre>
<h3>Шаг 4 - Правило с привязкой к конкретному интерфейсу</h3>
<p>Если у тебя несколько WAN-интерфейсов с разным MTU - применяй правило только к нужному.</p>
<pre><code class="language-bash">
# Только для PPPoE-интерфейса на входе:
/ip firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
in-interface=pppoe-out1 \
action=change-mss \
new-mss=clamp-to-pmtu \
comment="MSS Clamping inbound pppoe-out1"
# Только для PPPoE-интерфейса на выходе:
/ip firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
out-interface=pppoe-out1 \
action=change-mss \
new-mss=clamp-to-pmtu \
comment="MSS Clamping outbound pppoe-out1"
</code></pre>
<h3>Шаг 5 - MSS Clamping для IPv6</h3>
<p>Про IPv6 всегда забывают. Если у тебя есть IPv6 - нужны отдельные правила.</p>
<pre><code class="language-bash">
# MSS Clamping для IPv6:
/ipv6 firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
action=change-mss \
new-mss=clamp-to-pmtu \
comment="MSS Clamping IPv6 clamp-to-pmtu"
# Проверяем:
/ipv6 firewall mangle print
</code></pre>
<p>В IPv6 фрагментация на промежуточных узлах запрещена протоколом - только отправитель может фрагментировать. Поэтому PMTUD в IPv6 критичен, а MSS Clamping здесь ещё важнее чем в IPv4.</p>
<h3>Шаг 6 - Правило для исходящих соединений самого роутера</h3>
<pre><code class="language-bash">
# Если сам роутер инициирует TCP-соединения (fetch, обновления):
/ip firewall mangle add \
chain=output \
protocol=tcp \
tcp-flags=syn \
action=change-mss \
new-mss=clamp-to-pmtu \
comment="MSS Clamping router outbound"
</code></pre>
<h3>Проверка правил через Winbox</h3>
<p>IP - Firewall - Mangle. Правило должно быть с зелёной галочкой (enabled). Поле "Bytes" должно расти - значит правило применяется к трафику. Если Bytes = 0 после нескольких HTTPS-запросов с клиентского ПК - что-то не так с цепочкой или фильтрами.</p>
<h2>Настройка MSS Clamping на Keenetic</h2>
<h3>Системные требования</h3>
<table>
<thead>
<tr>
<th>Компонент</th>
<th>Версия</th>
<th>Примечание</th>
</tr>
</thead>
<tbody>
<tr>
<td>KeeneticOS</td>
<td>3.x и выше</td>
<td>CLI adjust-mss поддерживается с 3.x</td>
</tr>
<tr>
<td>Модели</td>
<td>Все с KeeneticOS</td>
<td>Keenetic Extra, Giga, Ultra и др.</td>
</tr>
<tr>
<td>Доступ</td>
<td>Администратор</td>
<td>Нужен для изменения параметров WAN</td>
</tr>
</tbody>
</table>
<p>На момент публикации актуальна KeeneticOS 4.x. Проверь актуальную версию на <a href="https://keenetic.ru/support" target="_blank" rel="noopener noreferrer">keenetic.ru</a>.</p>
<h3>Способ 1 - Через веб-интерфейс Keenetic</h3>
<p>Заходишь в веб-интерфейс роутера (обычно 192.168.1.1 или my.keenetic.net).</p>
<p>Путь: <strong>Интернет - выбираешь нужное подключение (PPPoE, L2TP, etc.) - кнопка "Изменить" - раздел "Дополнительно"</strong>.</p>
<p>Ищешь поле "Ограничение MSS TCP" или "TCP MSS". Вводишь значение:</p>
<ul>
<li>PPPoE: 1452</li>
<li>L2TP: считай по таблице выше</li>
<li>Если не знаешь - ставь 1452, это безопасное значение для большинства случаев</li>
</ul>
<p>Сохраняешь. Роутер применяет автоматически.</p>
<h3>Способ 2 - Через CLI Keenetic</h3>
<p>Подключись по SSH или через веб-консоль (Управление - Командная строка).</p>
<pre><code class="language-bash">
# Переходим к настройке PPPoE-интерфейса:
interface PPPoE0
# Устанавливаем MSS:
ip tcp adjust-mss 1452
# Для автоматической подстройки (если поддерживается):
ip tcp adjust-mss pmtu
# Выходим из режима интерфейса:
exit
# Сохраняем конфигурацию:
system configuration save
</code></pre>
"Важно
<br />
Синтаксис CLI Keenetic зависит от версии KeeneticOS. Перед применением проверь актуальный синтаксис командой help ip tcp в консоли роутера. В некоторых версиях команда называется ip tcp mss вместо ip tcp adjust-mss.<br />
<h3>Проверка на Keenetic</h3>
<pre><code class="language-bash">
# Смотрим интерфейсы и их состояние:
show interface
# Или через веб: Системный монитор - Интерфейсы
# Смотрим MTU активного WAN-интерфейса
</code></pre>
<h2>Диагностика: как определить проблему с MSS до настройки</h2>
<p>Не трогай ничего, пока не убедился что проблема именно в MSS. Вот полный инструментарий.</p>
<h3>Метод 1 - Ping с флагом Don't Fragment (быстрая проверка)</h3>
<p>На Windows:</p>
<pre><code class="language-bash">
# Проверяем MTU 1500:
ping 8.8.8.8 -f -l 1472
# -f = Don't Fragment
# -l 1472 = payload (1472 + 28 байт заголовков = 1500 байт итого)
# Если тайм-аут - уменьшаем:
ping 8.8.8.8 -f -l 1464
ping 8.8.8.8 -f -l 1452
ping 8.8.8.8 -f -l 1444
# Нашли максимальное значение которое проходит - это наш MTU payload
# MTU = найденное_значение + 28
# MSS = MTU - 40
</code></pre>
<p>На Linux/macOS:</p>
<pre><code class="language-bash">
# Linux:
ping -M do -s 1472 8.8.8.8
# macOS:
ping -D -s 1472 8.8.8.8
# Если ответ: "Frag needed and DF set" или "Message too long" - MTU меньше 1500
# Уменьшаем -s до получения ответа
</code></pre>
<h3>Метод 2 - tcpdump для захвата MSS в SYN-пакетах</h3>
<pre><code class="language-bash">
# Захватываем SYN-пакеты и смотрим поле MSS:
sudo tcpdump -i eth0 "tcp[tcpflags] & tcp-syn != 0" -v 2>/dev/null | grep -E "MSS|mss"
# Более подробный захват:
sudo tcpdump -i eth0 -n 'tcp[tcpflags] == tcp-syn' -v | head -40
# Ищем строку вида:
# options [mss 1460,...]
# Если видим MSS 1460 при PPPoE - проблема подтверждена
</code></pre>
<h3>Метод 3 - Wireshark (визуально)</h3>
<p>Фильтр: <code>tcp.flags.syn == 1</code></p>
<p>В деталях пакета: TCP - Options - Maximum segment size. Смотришь что анонсирует <a href="https://it-apteka.com/kakoj-vpn-server-ustanovit-na-ubuntu-dlja-nativnogo-podkljuchenija/" title="Настройка IKEv2 VPN сервера на Ubuntu 24.04: StrongSwan без лишних клиентов" target="_blank" rel="noopener" data-wpil-monitor-id="2776">клиент и что отвечает сервер</a>. Если оба показывают 1460 при PPPoE-подключении - MSS Clamping не работает.</p>
<h3>Метод 4 - MTR для поиска узкого места по пути</h3>
<pre><code class="language-bash">
# Linux - MTR с увеличенным размером пакета:
mtr --report --psize 1400 8.8.8.8
# Если видишь 100% потери на каком-то хопе при большом размере - вот узкое место
</code></pre>
<h3>Метод 5 - Torch на MikroTik</h3>
<pre><code class="language-bash">
# Мониторинг трафика на интерфейсе в реальном времени:
/tool torch interface=pppoe-out1 ip-protocol=tcp
# Смотрим размеры пакетов. Если видишь что пакеты > 1452 байт идут через PPPoE - проблема
</code></pre>
<h3>Быстрый тест HTTPS через curl</h3>
<pre><code class="language-bash">
# Тестируем TLS-рукопожатие с выводом времени:
curl -v --connect-timeout 10 https://example.com 2>&1 | head -30
# Если зависает на "SSL handshake" или "Trying X.X.X.X:443..." -
# это симптом проблемы с MSS при TLS ClientHello
# Сравниваем HTTP и HTTPS:
curl -v --connect-timeout 5 http://example.com > /dev/null 2>&1 && echo "HTTP OK"
curl -v --connect-timeout 5 https://example.com > /dev/null 2>&1 && echo "HTTPS OK"
</code></pre>
<h2>Проверка результата после настройки MSS Clamping</h2>
<h3>Проверка на MikroTik</h3>
<pre><code class="language-bash">
# Проверяем что правило активно и обрабатывает пакеты:
/ip firewall mangle print stats
# Должны видеть рост счётчика Bytes и Packets в правиле MSS Clamping
# Если счётчики не растут после нескольких минут работы - правило не применяется
# Проверяем счётчик конкретного правила (например rule #0):
/ip firewall mangle print stats where comment~"MSS"
# Смотрим логи (если включено логирование):
/log print where topics~"firewall"
</code></pre>
<h3>Функциональная проверка</h3>
<pre><code class="language-bash">
# С клиентского ПК за роутером:
# 1. Откройте несколько HTTPS-сайтов - должны открываться без зависания
# 2. Проверьте специфически тяжёлые сайты (много расширений TLS): github.com, google.com
# 3. Проверьте корпоративные порталы на TLS если именно они не работали
# Проверка через curl с подробным выводом TLS:
curl -v --tlsv1.3 https://github.com 2>&1 | grep -E "Connected|SSL|TLS|certificate"
# Должны увидеть:
# * Connected to github.com
# * SSL connection using TLSv1.3
# * Server certificate: ...
# Без зависания
</code></pre>
<h3>Проверка что MSS действительно изменился (tcpdump)</h3>
<pre><code class="language-bash">
# На Linux-машине за роутером, или на самом роутере если есть доступ:
sudo tcpdump -i any 'tcp[tcpflags] & tcp-syn != 0' -v 2>/dev/null | grep mss
# До настройки: options [mss 1460, ...]
# После настройки: options [mss 1452, ...]
# Если MSS изменился - MSS Clamping работает
</code></pre>
<h2>Troubleshooting: ошибки при настройке MSS Clamping</h2>
<h3>Ошибка 1 - MSS Clamping настроен, но HTTPS всё равно виснет</h3>
"Симптом"
<br />
Правило в mangle создано, счётчики растут, но HTTPS продолжает зависать.<br />
<p>Причины и решения:</p>
<ul>
<li><strong>Правило применяется к неправильному chain.</strong> Если трафик проходит через роутер - нужен chain=forward. Если роутер сам инициирует соединения - chain=output. Проверь chain.</li>
<li><strong>Неправильный интерфейс в фильтре.</strong> Если указал in-interface=ether1, а трафик идёт через pppoe-out1 - правило не применяется. Убери фильтр по интерфейсу или укажи правильный.</li>
<li><strong>Слишком большое значение MSS.</strong> clamp-to-pmtu берёт MTU исходящего интерфейса. Если MTU определяется неправильно - поставь фиксированное значение. Для PPPoE попробуй 1452, если не помогает - 1440.</li>
<li><strong>Проблема не в MSS.</strong> Проверь DNS (nslookup github.com), маршрутизацию, наличие proxy.</li>
</ul>
<pre><code class="language-bash">
# Проверяем MTU исходящего интерфейса (что видит clamp-to-pmtu):
/interface print detail where type=pppoe-out
# Смотрим поле actual-mtu
# Если actual-mtu показывает 1500 при PPPoE - MTU определяется неправильно
# Используй фиксированное значение:
/ip firewall mangle set [find comment~"MSS"] new-mss=1452
</code></pre>
<h3>Ошибка 2 - Счётчики правила не растут</h3>
"Симптом"
<br />
Правило создано, но Bytes и Packets остаются на нуле даже после активного использования HTTPS.<br />
<pre><code class="language-bash">
# Проверяем порядок правил - важен:
/ip firewall mangle print
# Если выше есть правило с action=passthrough или с accept
# которое захватывает тот же трафик - оно выполняется первым.
# MSS Clamping должен быть перед такими правилами или они не должны его блокировать.
# Проверяем, точно ли трафик идёт через chain=forward:
# Добавляем тестовое правило с логированием:
/ip firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
action=log \
log-prefix="SYN_TEST " \
passthrough=yes \
comment="DEBUG SYN traffic"
# Смотрим логи:
/log print where message~"SYN_TEST"
# Если видим записи - трафик идёт через chain=forward, проблема в другом
# После теста удаляем debug-правило:
/ip firewall mangle remove [find comment="DEBUG SYN traffic"]
</code></pre>
<h3>Ошибка 3 - HTTPS работает но медленно после настройки MSS</h3>
"Симптом"
<br />
HTTPS заработал, но скорость упала по сравнению с HTTP или предыдущей настройкой.<br />
<p>Причина: MSS выставлен слишком маленьким. Например, 576 байт "на всякий случай". Overhead на заголовки вырастает в разы, производительность падает.</p>
<pre><code class="language-bash">
# Проверяем текущее значение MSS в правиле:
/ip firewall mangle print detail where comment~"MSS"
# Если new-mss слишком мало - исправляем:
# Для PPPoE:
/ip firewall mangle set [find comment~"MSS Clamping PPPoE"] new-mss=1452
# Или переключаемся на clamp-to-pmtu:
/ip firewall mangle set [find comment~"MSS"] new-mss=clamp-to-pmtu
</code></pre>
<h3>Ошибка 4 - IPv6 HTTPS зависает, IPv4 работает</h3>
"Симптом"
<br />
После настройки MSS Clamping для IPv4 всё заработало. Но сайты с IPv6 продолжают зависать.<br />
<pre><code class="language-bash">
# Забыли про IPv6 mangle. Добавляем:
/ipv6 firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
action=change-mss \
new-mss=clamp-to-pmtu \
comment="MSS Clamping IPv6"
# Проверяем:
/ipv6 firewall mangle print stats
# Для IPv6 также нужно правило для output:
/ipv6 firewall mangle add \
chain=output \
protocol=tcp \
tcp-flags=syn \
action=change-mss \
new-mss=clamp-to-pmtu \
comment="MSS Clamping IPv6 output"
</code></pre>
<h3>Ошибка 5 - Дублирующиеся правила MSS Clamping</h3>
<p>Если несколько правил с одинаковым действием - они не сломают сеть, но создают лишнюю нагрузку и путаницу. Чистим.</p>
<pre><code class="language-bash">
# Смотрим все правила mangle:
/ip firewall mangle print
# Удаляем дубли (по номеру правила):
/ip firewall mangle remove numbers=3,4
# Или по комментарию - осторожно, удалит все совпадения:
/ip firewall mangle remove [find comment~"MSS Clamping"]
# После этого добавь правило заново - убедись что осталось одно нужное
</code></pre>
<h3>Ошибка 6 - MSS Clamping ломает IPsec туннель</h3>
"Симптом"
<br />
После добавления MSS Clamping перестал работать site-to-site IPsec туннель или данные по туннелю передаются некорректно.<br />
<pre><code class="language-bash">
# IPsec-трафик нужно исключить из MSS Clamping или применять аккуратно.
# Проверяем политики IPsec:
/ip ipsec policy print
# Для site-to-site IPsec используй отдельное правило с фильтрацией по интерфейсу:
/ip firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
out-interface=!lo \
ipsec-policy=out,ipsec \
action=change-mss \
new-mss=1378 \
comment="MSS Clamping IPsec outbound"
/ip firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
in-interface=!lo \
ipsec-policy=in,ipsec \
action=change-mss \
new-mss=1378 \
comment="MSS Clamping IPsec inbound"
</code></pre>
<h2>Таблица портов и протоколов</h2>
<table>
<thead>
<tr>
<th>Протокол</th>
<th>Порт</th>
<th>Направление</th>
<th>Зачем нужен для MSS</th>
</tr>
</thead>
<tbody>
<tr>
<td>HTTPS</td>
<td>TCP 443</td>
<td>Исходящий</td>
<td>Основной затронутый протокол</td>
</tr>
<tr>
<td>HTTP</td>
<td>TCP 80</td>
<td>Исходящий</td>
<td>Менее чувствителен к MSS</td>
</tr>
<tr>
<td>ICMP Type 3 Code 4</td>
<td>-</td>
<td>Входящий</td>
<td>Fragmentation Needed - нужен для PMTUD</td>
</tr>
<tr>
<td>PPPoE Discovery</td>
<td>ETH 0x8863/0x8864</td>
<td>Оба</td>
<td>Добавляет 8 байт overhead к MTU</td>
</tr>
<tr>
<td>GRE</td>
<td>IP proto 47</td>
<td>Оба</td>
<td>24 байта overhead</td>
</tr>
<tr>
<td>IPsec ESP</td>
<td>UDP 4500 / IP proto 50</td>
<td>Оба</td>
<td>~50-80 байт overhead</td>
</tr>
<tr>
<td>WireGuard</td>
<td>UDP 51820</td>
<td>Оба</td>
<td>~80 байт overhead</td>
</tr>
</tbody>
</table>
<h2>Когда MSS Clamping нужен, а когда нет</h2>
<h3>Настраивай обязательно:</h3>
<ul>
<li>PPPoE-подключение к провайдеру (MTU 1492)</li>
<li>L2TP, PPTP, GRE туннели</li>
<li>IPsec (ESP) - site-to-site и road warrior</li>
<li>WireGuard, OpenVPN</li>
<li>LTE/4G/5G-подключения с нестандартным MTU</li>
<li>Туннель внутри туннеля (каждый уровень добавляет overhead)</li>
<li>Site-to-site VPN для объединения офисов</li>
</ul>
<h3>Не трогай:</h3>
<ul>
<li>Обычное Ethernet-подключение без туннелей (MTU 1500, MSS 1460 - всё штатно)</li>
<li>PMTUD работает корректно и ICMP не блокируется</li>
<li>Медленная загрузка из-за DNS или proxy - диагностируй правильно</li>
<li>MSS уже настроен провайдером на своём оборудовании</li>
</ul>
<h2>Безопасность при настройке MSS Clamping</h2>
<p>MSS Clamping сам по себе безопасен - он работает только с SYN-пакетами при открытии соединения, не расшифровывает и не модифицирует данные.</p>
<p>Но пока открыт Firewall Mangle - проверь общее состояние безопасности:</p>
<pre><code class="language-bash">
# Проверяем что базовые правила firewall на месте:
/ip firewall filter print
# Должны быть правила:
# - accept established,related
# - drop invalid
# - accept input from LAN
# - drop input from WAN (кроме нужных портов)
# Проверяем что нет посторонних открытых правил:
/ip firewall filter print where action=accept chain=input
# Убеждаемся что Winbox доступен только из LAN, не из WAN:
/ip firewall filter print where dst-port=8291
</code></pre>
"Не
<br />
Перед изменениями в firewall mangle всегда делай бэкап конфигурации. Одна опечатка в правиле может заблокировать весь транзитный трафик.<br />
<h2>Резервное копирование конфигурации MikroTik</h2>
<pre><code class="language-bash">
# Бэкап перед изменениями (бинарный - всё включая пароли):
/system backup save name=before-mss-clamping
# Экспорт конфигурации в текст (читаемый, без паролей):
/export file=before-mss-clamping-export
# Скачай файлы через Winbox: Files - скачай .backup и .rsc
# Или через SCP:
# scp admin@192.168.88.1:before-mss-clamping.backup ./
# Восстановление из бэкапа если что-то сломалось:
/system backup load name=before-mss-clamping
</code></pre>
<h2>Профилактика: как не сломать снова</h2>
<ul>
<li><strong>Документируй MTU каждого интерфейса</strong> - добавляй комментарий к правилу mangle с реальным MTU. Через год сам скажешь себе спасибо.</li>
<li><strong>Используй clamp-to-pmtu как дефолт</strong> - динамически подстраивается, не нужно пересчитывать при смене провайдера.</li>
<li><strong>Не блокируй ICMP Type 3 полностью</strong> - можешь блокировать echo-request (ping), но Destination Unreachable нужен для PMTUD. Правило в firewall filter: accept icmp where icmp-options=3:4.</li>
<li><strong>Проверяй MSS после смены провайдера</strong> - новый провайдер может иметь другой MTU.</li>
<li><strong>При добавлении нового туннеля</strong> - сразу пересчитывай MSS. Не "потом".</li>
<li><strong>Мониторь ICMP unreachable</strong> - рост таких сообщений сигнализирует о проблемах с PMTUD.</li>
</ul>
<h2>Обновление RouterOS с MSS Clamping</h2>
<pre><code class="language-bash">
# Перед обновлением RouterOS:
# 1. Бэкап:
/system backup save name=pre-update-backup
# 2. Проверь changelog на изменения в firewall/mangle:
# https://mikrotik.com/download/changelogs
# 3. Обновляй в тестовой среде сначала если есть возможность
# После обновления:
# 4. Проверь что правила mangle на месте:
/ip firewall mangle print
# 5. Проверь счётчики:
/ip firewall mangle print stats
# 6. Функциональный тест HTTPS с клиентского ПК
</code></pre>
<h2>Альтернативные решения</h2>
<h3>Вариант 1 - Уменьшить MTU интерфейса на MikroTik</h3>
<p>Вместо MSS Clamping можно уменьшить MTU самого интерфейса. Тогда сетевой стек сам будет генерировать пакеты правильного размера.</p>
<pre><code class="language-bash">
# Уменьшаем MTU Ethernet-интерфейса:
/interface ethernet set ether1 mtu=1492
# Минус: влияет на весь трафик через интерфейс, не только TCP.
# MSS Clamping точечнее - работает только с SYN-пакетами.
</code></pre>
<h3>Вариант 2 - Разрешить ICMP Type 3 Code 4 в firewall</h3>
<p>Если PMTUD работает корректно - MSS Clamping не нужен. Убедись что ICMP Fragmentation Needed не блокируется.</p>
<pre><code class="language-bash">
# На MikroTik - разрешаем ICMP Fragmentation Needed:
/ip firewall filter add \
chain=input \
protocol=icmp \
icmp-options=3:4 \
action=accept \
comment="Allow ICMP Fragmentation Needed for PMTUD" \
place-before=0
# Это позволит PMTUD работать без MSS Clamping
</code></pre>
<h3>Вариант 3 - ip tcp adjust-mss на Linux/iptables</h3>
<pre><code class="language-bash">
# На Linux-роутере (iptables):
iptables -t mangle -A FORWARD -p tcp --tcp-flags SYN,RST SYN \
-j TCPMSS --clamp-mss-to-pmtu
# nftables (современный вариант):
nft add rule ip mangle FORWARD tcp flags syn / syn,rst \
tcp option maxseg size set rt mtu
# Сохраняем:
iptables-save > /etc/iptables/rules.v4
</code></pre>
<h2>FAQ</h2>
<h3>Почему HTTPS не работает после подключения VPN, а HTTP работает нормально?</h3>
<p>VPN-туннель добавляет свои заголовки к каждому пакету - это уменьшает реальный MTU канала. TLS ClientHello при HTTPS-рукопожатии передаётся с флагом Don't Fragment и имеет значительный размер. Если MTU канала уменьшился из-за VPN, а MSS не подстроен - ClientHello не проходит, и браузер зависает на соединении. Решение: настроить MSS Clamping на роутере или VPN-сервере.</p>
<h3>Как проверить текущий MSS который анонсирует мой компьютер?</h3>
<pre><code class="language-bash">
# Windows - через Wireshark или PowerShell:
# В Wireshark: tcp.flags.syn == 1 - смотри TCP Options -> Maximum segment size
# Linux - через ss или tcpdump:
ss -tin dst 8.8.8.8
# MikroTik - через torch или packet sniffer:
/tool sniffer start
/tool sniffer packet print
/tool sniffer stop
</code></pre>
<h3>Что лучше - clamp-to-pmtu или фиксированное значение MSS?</h3>
<p>Для большинства случаев <code>clamp-to-pmtu</code> предпочтительнее - он динамически определяет максимально допустимый MSS по MTU исходящего интерфейса, не требует ручного пересчёта и автоматически адаптируется при смене канала. Фиксированное значение оправдано когда <code>clamp-to-pmtu</code> определяет MTU неправильно (бывает на некоторых туннельных интерфейсах), или когда нужно гарантированно ограничить MSS конкретным значением независимо от интерфейса.</p>
<h3>Нужно ли настраивать MSS Clamping если провайдер уже это делает?</h3>
<p>Если провайдер настраивает MSS Clamping на своём оборудовании для PPPoE - твой <a href="https://it-apteka.com/mikrotik-hap-obzor-vseh-modelej-harakteristiki-i-nastrojka-routera/" title="MikroTik hAP: обзор всех моделей, характеристики и настройка роутера" target="_blank" rel="noopener" data-wpil-monitor-id="2122">роутер может не нуждаться в дополнительной настройке</a> для самого PPPoE. Но если у тебя поверх PPPoE ещё VPN-туннель - добавляешь свой слой overhead, и правило нужно уже твоему роутеру. Диагностируй по факту: работает HTTPS нормально - не трогай.</p>
<h3>Почему MSS Clamping не работает для уже установленных соединений?</h3>
<p>MSS Clamping работает только с SYN-пакетами - теми, которые открывают новое TCP-соединение. Установившиеся сессии не затрагиваются: MSS согласован при рукопожатии и изменить его без разрыва соединения нельзя. Поэтому после добавления правила mangle уже активные соединения продолжат работу со старым MSS. Новые соединения получат правильный MSS сразу.</p>
<h3>Какой MSS выставить для WireGuard?</h3>
<p>WireGuard добавляет примерно 60-80 байт overhead в зависимости от конфигурации. Если внешний MTU 1500, то MTU WireGuard-интерфейса обычно 1420, MSS = 1380. Рекомендуется использовать <code>clamp-to-pmtu</code> - RouterOS сам определит MTU wg-интерфейса. Или явно задай MTU в настройках WireGuard-пира: <code>/interface wireguard set wg0 mtu=1420</code>.</p>
<h2>Прогноз и итоги</h2>
<p>Сделали следующее: разобрали механизм MSS от формулы до поведения TLS ClientHello, настроили MSS Clamping на MikroTik через mangle с <code>clamp-to-pmtu</code>, добавили IPv6, настроили Keenetic через веб и CLI, прошли через полный набор инструментов диагностики.</p>
<p>Теперь HTTPS-сессии будут открываться корректно через PPPoE, <a href="https://it-apteka.com/proxy-arp-mikrotik-kak-probrosit-arp-cherez-vpn-tunnel/" title="Proxy ARP MikroTik: как пробросить ARP через VPN туннель" target="_blank" rel="noopener" data-wpil-monitor-id="2732">VPN и любые другие туннели</a>. MSS Clamping - это не хак и не workaround, это стандартная практика для любой <a class="wpil_keyword_link" href="https://it-apteka.com/category/networks/" target="_blank" rel="noopener" title="Сети" data-wpil-keyword-link="linked" data-wpil-monitor-id="2108">сети</a> с инкапсуляцией. Если у тебя сеть с туннелями без MSS Clamping - это не "работает само", это "ещё не сломалось при определённых условиях".</p>
"Не
<br />
Если после настройки HTTPS всё ещё виснет — пиши в комментарии. Опиши тип подключения, что показывает ping с флагом DF и счётчики mangle. Разберём конкретный случай.<br />
За что бьёмся
TCP MSS (Maximum Segment Size) — максимальный размер полезной нагрузки одного TCP-сегмента. Формула: MSS = MTU — 40 байт. При PPPoE, VPN-туннелях и любой инкапсуляции MTU уменьшается. Если MSS не подстроен, а ICMP заблокирован провайдером, HTTPS-сессии зависают на TLS-рукопожатии. Решение: MSS Clamping — одно правило в mangle на
MikroTik или один параметр в настройках Keenetic.
Диагноз: HTTPS виснет, HTTP летит, вы уже всё перепробовали
HTTP работает. HTTPS крутит колесо и выдаёт тайм-аут. VPN поднят, пинги идут, а корпоративный портал на TLS не открывается. PPPoE подключили — лёгкие сайты летят, тяжёлые страницы зависают.
Это не браузер, не сертификат и не DNS. В девяти случаях из десяти — неправильный MSS. Разберём, что это такое, почему ломает именно HTTPS, и закроем проблему командами для MikroTik и Keenetic.
Что получишь после прочтения:
- Понимание механизма MSS и его связи с MTU
- Готовые команды MikroTik (RouterOS 6.x и 7.x) и Keenetic
- Инструменты диагностики — найдёшь проблему до того как что-то менять
- Troubleshooting типичных ошибок при настройке MSS Clamping
- IPv6 — отдельный блок, потому что про него всегда забывают
- FAQ под реальные вопросы из поиска
Время на настройку: 5-10 минут. Время на диагностику: 15-20 минут если проблема нестандартная.
Что такое MSS (Maximum Segment Size) и как он связан с MTU
MSS — это максимальный размер полезной нагрузки одного TCP-сегмента без учёта заголовков IP и TCP. Проще говоря: сколько байт данных влезает в один пакет на уровне TCP.
MSS неразрывно связан с MTU (Maximum Transmission Unit) — максимальным размером кадра на уровне канала передачи данных. Связь прямая:
# Формула расчёта MSS:
MSS = MTU - 20 (IP header) - 20 (TCP header)
MSS = MTU - 40
# Пример для стандартного Ethernet:
MSS = 1500 - 40 = 1460
# Пример для PPPoE:
# PPPoE добавляет 8 байт заголовка, поэтому MTU = 1492
MSS = 1492 - 40 = 1452
MSS анонсируется в момент TCP-рукопожатия — в пакете SYN. Каждая из сторон сообщает, какой максимальный сегмент она готова принять. Дальше соединение работает с наименьшим из двух значений.
Значения MSS для популярных типов соединений
| Тип соединения |
MTU |
Overhead |
MSS |
Примечание |
| Ethernet (стандарт) |
1500 |
40 |
1460 |
Базовое значение |
| PPPoE (DSL/GPON) |
1492 |
40 |
1452 |
PPPoE = 8 байт overhead |
| L2TP без шифрования |
1460 |
40 |
1420 |
L2TP header ~40 байт |
| L2TP + IPsec |
1418 |
40 |
1378 |
IPsec ESP добавляет ~50 байт |
| IPsec (ESP, AES-256) |
1418 |
40 |
1378 |
Зависит от cipher suite |
| GRE-туннель |
1476 |
40 |
1436 |
GRE header = 24 байта |
| WireGuard VPN |
1420 |
40 |
1380 |
WireGuard overhead ~80 байт |
| OpenVPN (UDP) |
~1400 |
40 |
~1360 |
Зависит от cipher и компрессии |
| GRE поверх PPPoE |
1468 |
40 |
1428 |
Складываем overhead оба уровня |
Архитектура: как MSS анонсируется в TCP-рукопожатии
%%{init: {
'theme': 'base',
'themeVariables': {
'primaryColor': '#f8fafc',
'primaryTextColor': '#1e293b',
'primaryBorderColor': '#94a3b8',
'noteBkgColor': '#fefce8',
'noteTextColor': '#713f12',
'noteBorderColor': '#fbbf24',
'actorBkg': '#f8fafc',
'actorBorder': '#94a3b8',
'actorTextColor': '#1e293b',
'fontSize': '15px',
'fontFamily': 'ui-sans-serif, system-ui, sans-serif'
},
'sequence': {
'mirrorActors': false,
'messageAlign': 'center',
'actorMargin': 100,
'width': 160,
'noteMargin': 12
}
}}%%
sequenceDiagram
participant C as Клиент (MSS 1460)
participant R as Роутер PPPoE
participant S as Сервер (MSS 1460)
C->>R: SYN, MSS=1460
Note over R: MSS Clamping: 1460 -> 1452
R->>S: SYN, MSS=1452
S->>R: SYN-ACK, MSS=1452
R->>C: SYN-ACK, MSS=1452
C->>S: ACK (сессия открыта, MSS=1452)
Note over C,S: Оба передают сегменты <= 1452 байт
Без MSS Clamping клиент анонсирует MSS=1460, сервер соглашается. Но пакеты по пути через PPPoE-интерфейс не влезают в MTU=1492 при размере сегмента 1460+40=1500 байт. Точнее, влезают ровно впритык для IPv4 - но TLS ClientHello с расширениями легко выходит за эти рамки.
Почему именно HTTPS зависает, а HTTP работает
Здесь важно понять механизм Path MTU Discovery (PMTUD). Когда пакет не влезает в MTU промежуточного узла, маршрутизатор должен либо фрагментировать его, либо - если установлен флаг DF (Don't Fragment) - отправить назад ICMP Type 3 Code 4 "Fragmentation Needed". Получив это сообщение, отправитель снижает размер сегмента.
Проблема: многие провайдеры и файрволы блокируют ICMP. Полностью. Из-за паранойи, из-за кривой политики безопасности, из-за того что "так было настроено в 2009 году и никто не трогал". В результате отправитель никогда не узнаёт, что пакет не прошёл. Пакеты молча отбрасываются, соединение зависает.
Почему HTTP страдает меньше
HTTP-запрос типично мал: GET /, Host, User-Agent - влезает в один пакет хорошо. Ответ сервера разбивается на мелкие сегменты. Если один потерялся - TCP ретрансмиссия, и всё равно доходит.
TLS-рукопожатие устроено иначе. Пакет ClientHello в TLS 1.3 содержит:
- список поддерживаемых cipher suites (десятки вариантов)
- список расширений: SNI, ALPN, session tickets, key_share
- публичный ключ Diffie-Hellman (32-64 байта)
- supported_groups, signature_algorithms
Итого ClientHello легко достигает 400-600 байт. Это нормально. Но пакет передаётся с флагом DF=1. Если на пути есть PPPoE или туннель с уменьшенным MTU - и ICMP заблокирован - этот пакет молча дропается. Браузер ждёт ответа, таймаут, retry, снова таймаут.
Поток данных при заблокированном PMTUD
%%{init: {
'theme': 'base',
'themeVariables': {
'primaryColor': '#ffffff',
'primaryTextColor': '#1e293b',
'primaryBorderColor': '#94a3b8',
'lineColor': '#64748b',
'fontSize': '15px',
'fontFamily': 'ui-sans-serif, system-ui, sans-serif'
},
'flowchart': {'curve': 'linear', 'nodeSpacing': 50, 'rankSpacing': 50}
}}%%
flowchart TD
A["Клиент отправляет TLS ClientHello (DF=1, размер > MTU туннеля)"] --> B["Промежуточный роутер PPPoE/VPN"]
B --> C{"Пакет влезает в MTU?"}
C -->|"Да"| D["Пакет проходит дальше"]
C -->|"Нет"| E{"ICMP разрешён?"}
E -->|"Да (PMTUD работает)"| F["ICMP Fragmentation Needed -> клиент снижает MSS"]
E -->|"Нет (ICMP заблокирован)"| G["Пакет дропается МОЛЧА"]
G --> H["Клиент ждёт ответа - тайм-аут"]
H --> I["Retry - снова тайм-аут"]
I --> J["HTTPS не работает"]
F --> K["HTTPS работает после адаптации"]
D --> K
style G fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#b91c1c
style J fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#b91c1c
style K fill:#f8fafc,stroke:#22c55e,stroke-width:2px,color:#15803d
style F fill:#f8fafc,stroke:#22c55e,stroke-width:2px,color:#15803d
Что такое MSS Clamping и как он решает проблему
MSS Clamping - механизм, при котором маршрутизатор на лету изменяет значение MSS в TCP SYN-пакетах, приводя его к безопасному значению для данного канала.
Ключевые особенности:
- Работает только с SYN и SYN-ACK пакетами - только при открытии нового TCP-соединения. Установившиеся сессии не затрагиваются.
- Не ломает соединение - уменьшает анонсируемый MSS до допустимого предела.
- Решает проблему заблокированного PMTUD - стороны изначально договариваются на правильный размер сегмента, до первого большого пакета.
- Прозрачно для конечных узлов - клиент и сервер не знают, что кто-то подправил их SYN.
Схема работы MSS Clamping
%%{init: {
'theme': 'base',
'themeVariables': {
'primaryColor': '#ffffff',
'primaryTextColor': '#1e293b',
'primaryBorderColor': '#94a3b8',
'lineColor': '#64748b',
'fontSize': '15px',
'fontFamily': 'ui-sans-serif, system-ui, sans-serif'
},
'flowchart': {'curve': 'linear', 'nodeSpacing': 50, 'rankSpacing': 50}
}}%%
flowchart LR
A["Клиент SYN MSS=1460"] --> B["MikroTik Mangle"]
B --> C["change-mss clamp-to-pmtu"]
C --> D["SYN MSS=1452 (PPPoE)"]
D --> E["Сервер принимает"]
style B fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style C fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
Настройка MSS Clamping на MikroTik
Системные требования
| Компонент |
Минимальная версия |
Рекомендуется |
Примечание |
| RouterOS |
6.40 |
7.x (LTS) |
clamp-to-pmtu доступен с 6.x |
| Тип устройства |
Любой MikroTik |
hEX, RB4011, CCR |
Mangle есть на всех |
| Права доступа |
full или write |
full |
Нужен доступ к Firewall |
На момент публикации актуальна RouterOS 7.18. Перед применением проверь свежие релизы на mikrotik.com/download.
Шаг 1 - Проверяем MTU интерфейса
Прежде чем что-то настраивать, смотрим что есть. Открой Terminal в Winbox или подключись по SSH.
# Смотрим все интерфейсы и их MTU:
/interface print detail
# Конкретно для PPPoE-подключения:
/interface pppoe-client print detail
# Проверяем MTU через ping с флагом DF:
/tool ping address=8.8.8.8 size=1472 do-not-fragment=yes count=4
# Если ответ есть - MTU 1500, MSS 1460
# Если тайм-аут - уменьшай size до получения ответа
# Бинарный поиск MTU:
/tool ping address=8.8.8.8 size=1452 do-not-fragment=yes count=2
/tool ping address=8.8.8.8 size=1464 do-not-fragment=yes count=2
/tool ping address=8.8.8.8 size=1453 do-not-fragment=yes count=2
Результат: знаешь реальный MTU канала. Теперь считаем MSS: MTU - 40.
Шаг 2 - MSS Clamping с автоматической подстройкой (рекомендуется)
Вариант с clamp-to-pmtu - динамически определяет допустимый MSS по MTU исходящего интерфейса. Не нужно вручную считать и обновлять значение при смене MTU.
# Основное правило - для транзитного трафика через роутер:
/ip firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
action=change-mss \
new-mss=clamp-to-pmtu \
comment="MSS Clamping IPv4 clamp-to-pmtu"
# Проверяем что правило создалось:
/ip firewall mangle print
Шаг 3 - MSS Clamping с фиксированным значением
Нужен если clamp-to-pmtu не даёт нужного результата или ты точно знаешь значение MTU. Для PPPoE с MTU 1492 MSS = 1452.
# Фиксированное значение для PPPoE:
/ip firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
action=change-mss \
new-mss=1452 \
comment="MSS Clamping PPPoE fixed 1452"
# Для L2TP/IPsec (MTU ~1418):
/ip firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
action=change-mss \
new-mss=1378 \
comment="MSS Clamping L2TP-IPsec fixed 1378"
# Для WireGuard (MTU 1420):
/ip firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
action=change-mss \
new-mss=1380 \
comment="MSS Clamping WireGuard fixed 1380"
Шаг 4 - Правило с привязкой к конкретному интерфейсу
Если у тебя несколько WAN-интерфейсов с разным MTU - применяй правило только к нужному.
# Только для PPPoE-интерфейса на входе:
/ip firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
in-interface=pppoe-out1 \
action=change-mss \
new-mss=clamp-to-pmtu \
comment="MSS Clamping inbound pppoe-out1"
# Только для PPPoE-интерфейса на выходе:
/ip firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
out-interface=pppoe-out1 \
action=change-mss \
new-mss=clamp-to-pmtu \
comment="MSS Clamping outbound pppoe-out1"
Шаг 5 - MSS Clamping для IPv6
Про IPv6 всегда забывают. Если у тебя есть IPv6 - нужны отдельные правила.
# MSS Clamping для IPv6:
/ipv6 firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
action=change-mss \
new-mss=clamp-to-pmtu \
comment="MSS Clamping IPv6 clamp-to-pmtu"
# Проверяем:
/ipv6 firewall mangle print
В IPv6 фрагментация на промежуточных узлах запрещена протоколом - только отправитель может фрагментировать. Поэтому PMTUD в IPv6 критичен, а MSS Clamping здесь ещё важнее чем в IPv4.
Шаг 6 - Правило для исходящих соединений самого роутера
# Если сам роутер инициирует TCP-соединения (fetch, обновления):
/ip firewall mangle add \
chain=output \
protocol=tcp \
tcp-flags=syn \
action=change-mss \
new-mss=clamp-to-pmtu \
comment="MSS Clamping router outbound"
Проверка правил через Winbox
IP - Firewall - Mangle. Правило должно быть с зелёной галочкой (enabled). Поле "Bytes" должно расти - значит правило применяется к трафику. Если Bytes = 0 после нескольких HTTPS-запросов с клиентского ПК - что-то не так с цепочкой или фильтрами.
Настройка MSS Clamping на Keenetic
Системные требования
| Компонент |
Версия |
Примечание |
| KeeneticOS |
3.x и выше |
CLI adjust-mss поддерживается с 3.x |
| Модели |
Все с KeeneticOS |
Keenetic Extra, Giga, Ultra и др. |
| Доступ |
Администратор |
Нужен для изменения параметров WAN |
На момент публикации актуальна KeeneticOS 4.x. Проверь актуальную версию на keenetic.ru.
Способ 1 - Через веб-интерфейс Keenetic
Заходишь в веб-интерфейс роутера (обычно 192.168.1.1 или my.keenetic.net).
Путь: Интернет - выбираешь нужное подключение (PPPoE, L2TP, etc.) - кнопка "Изменить" - раздел "Дополнительно".
Ищешь поле "Ограничение MSS TCP" или "TCP MSS". Вводишь значение:
- PPPoE: 1452
- L2TP: считай по таблице выше
- Если не знаешь - ставь 1452, это безопасное значение для большинства случаев
Сохраняешь. Роутер применяет автоматически.
Способ 2 - Через CLI Keenetic
Подключись по SSH или через веб-консоль (Управление - Командная строка).
# Переходим к настройке PPPoE-интерфейса:
interface PPPoE0
# Устанавливаем MSS:
ip tcp adjust-mss 1452
# Для автоматической подстройки (если поддерживается):
ip tcp adjust-mss pmtu
# Выходим из режима интерфейса:
exit
# Сохраняем конфигурацию:
system configuration save
Важно для Keenetic
Синтаксис CLI Keenetic зависит от версии KeeneticOS. Перед применением проверь актуальный синтаксис командой help ip tcp в консоли роутера. В некоторых версиях команда называется ip tcp mss вместо ip tcp adjust-mss.
Проверка на Keenetic
# Смотрим интерфейсы и их состояние:
show interface
# Или через веб: Системный монитор - Интерфейсы
# Смотрим MTU активного WAN-интерфейса
Диагностика: как определить проблему с MSS до настройки
Не трогай ничего, пока не убедился что проблема именно в MSS. Вот полный инструментарий.
Метод 1 - Ping с флагом Don't Fragment (быстрая проверка)
На Windows:
# Проверяем MTU 1500:
ping 8.8.8.8 -f -l 1472
# -f = Don't Fragment
# -l 1472 = payload (1472 + 28 байт заголовков = 1500 байт итого)
# Если тайм-аут - уменьшаем:
ping 8.8.8.8 -f -l 1464
ping 8.8.8.8 -f -l 1452
ping 8.8.8.8 -f -l 1444
# Нашли максимальное значение которое проходит - это наш MTU payload
# MTU = найденное_значение + 28
# MSS = MTU - 40
На Linux/macOS:
# Linux:
ping -M do -s 1472 8.8.8.8
# macOS:
ping -D -s 1472 8.8.8.8
# Если ответ: "Frag needed and DF set" или "Message too long" - MTU меньше 1500
# Уменьшаем -s до получения ответа
Метод 2 - tcpdump для захвата MSS в SYN-пакетах
# Захватываем SYN-пакеты и смотрим поле MSS:
sudo tcpdump -i eth0 "tcp[tcpflags] & tcp-syn != 0" -v 2>/dev/null | grep -E "MSS|mss"
# Более подробный захват:
sudo tcpdump -i eth0 -n 'tcp[tcpflags] == tcp-syn' -v | head -40
# Ищем строку вида:
# options [mss 1460,...]
# Если видим MSS 1460 при PPPoE - проблема подтверждена
Метод 3 - Wireshark (визуально)
Фильтр: tcp.flags.syn == 1
В деталях пакета: TCP - Options - Maximum segment size. Смотришь что анонсирует клиент и что отвечает сервер. Если оба показывают 1460 при PPPoE-подключении - MSS Clamping не работает.
Метод 4 - MTR для поиска узкого места по пути
# Linux - MTR с увеличенным размером пакета:
mtr --report --psize 1400 8.8.8.8
# Если видишь 100% потери на каком-то хопе при большом размере - вот узкое место
Метод 5 - Torch на MikroTik
# Мониторинг трафика на интерфейсе в реальном времени:
/tool torch interface=pppoe-out1 ip-protocol=tcp
# Смотрим размеры пакетов. Если видишь что пакеты > 1452 байт идут через PPPoE - проблема
Быстрый тест HTTPS через curl
# Тестируем TLS-рукопожатие с выводом времени:
curl -v --connect-timeout 10 https://example.com 2>&1 | head -30
# Если зависает на "SSL handshake" или "Trying X.X.X.X:443..." -
# это симптом проблемы с MSS при TLS ClientHello
# Сравниваем HTTP и HTTPS:
curl -v --connect-timeout 5 http://example.com > /dev/null 2>&1 && echo "HTTP OK"
curl -v --connect-timeout 5 https://example.com > /dev/null 2>&1 && echo "HTTPS OK"
Проверка результата после настройки MSS Clamping
Проверка на MikroTik
# Проверяем что правило активно и обрабатывает пакеты:
/ip firewall mangle print stats
# Должны видеть рост счётчика Bytes и Packets в правиле MSS Clamping
# Если счётчики не растут после нескольких минут работы - правило не применяется
# Проверяем счётчик конкретного правила (например rule #0):
/ip firewall mangle print stats where comment~"MSS"
# Смотрим логи (если включено логирование):
/log print where topics~"firewall"
Функциональная проверка
# С клиентского ПК за роутером:
# 1. Откройте несколько HTTPS-сайтов - должны открываться без зависания
# 2. Проверьте специфически тяжёлые сайты (много расширений TLS): github.com, google.com
# 3. Проверьте корпоративные порталы на TLS если именно они не работали
# Проверка через curl с подробным выводом TLS:
curl -v --tlsv1.3 https://github.com 2>&1 | grep -E "Connected|SSL|TLS|certificate"
# Должны увидеть:
# * Connected to github.com
# * SSL connection using TLSv1.3
# * Server certificate: ...
# Без зависания
Проверка что MSS действительно изменился (tcpdump)
# На Linux-машине за роутером, или на самом роутере если есть доступ:
sudo tcpdump -i any 'tcp[tcpflags] & tcp-syn != 0' -v 2>/dev/null | grep mss
# До настройки: options [mss 1460, ...]
# После настройки: options [mss 1452, ...]
# Если MSS изменился - MSS Clamping работает
Troubleshooting: ошибки при настройке MSS Clamping
Ошибка 1 - MSS Clamping настроен, но HTTPS всё равно виснет
Симптом
Правило в mangle создано, счётчики растут, но HTTPS продолжает зависать.
Причины и решения:
- Правило применяется к неправильному chain. Если трафик проходит через роутер - нужен chain=forward. Если роутер сам инициирует соединения - chain=output. Проверь chain.
- Неправильный интерфейс в фильтре. Если указал in-interface=ether1, а трафик идёт через pppoe-out1 - правило не применяется. Убери фильтр по интерфейсу или укажи правильный.
- Слишком большое значение MSS. clamp-to-pmtu берёт MTU исходящего интерфейса. Если MTU определяется неправильно - поставь фиксированное значение. Для PPPoE попробуй 1452, если не помогает - 1440.
- Проблема не в MSS. Проверь DNS (nslookup github.com), маршрутизацию, наличие proxy.
# Проверяем MTU исходящего интерфейса (что видит clamp-to-pmtu):
/interface print detail where type=pppoe-out
# Смотрим поле actual-mtu
# Если actual-mtu показывает 1500 при PPPoE - MTU определяется неправильно
# Используй фиксированное значение:
/ip firewall mangle set [find comment~"MSS"] new-mss=1452
Ошибка 2 - Счётчики правила не растут
Симптом
Правило создано, но Bytes и Packets остаются на нуле даже после активного использования HTTPS.
# Проверяем порядок правил - важен:
/ip firewall mangle print
# Если выше есть правило с action=passthrough или с accept
# которое захватывает тот же трафик - оно выполняется первым.
# MSS Clamping должен быть перед такими правилами или они не должны его блокировать.
# Проверяем, точно ли трафик идёт через chain=forward:
# Добавляем тестовое правило с логированием:
/ip firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
action=log \
log-prefix="SYN_TEST " \
passthrough=yes \
comment="DEBUG SYN traffic"
# Смотрим логи:
/log print where message~"SYN_TEST"
# Если видим записи - трафик идёт через chain=forward, проблема в другом
# После теста удаляем debug-правило:
/ip firewall mangle remove [find comment="DEBUG SYN traffic"]
Ошибка 3 - HTTPS работает но медленно после настройки MSS
Симптом
HTTPS заработал, но скорость упала по сравнению с HTTP или предыдущей настройкой.
Причина: MSS выставлен слишком маленьким. Например, 576 байт "на всякий случай". Overhead на заголовки вырастает в разы, производительность падает.
# Проверяем текущее значение MSS в правиле:
/ip firewall mangle print detail where comment~"MSS"
# Если new-mss слишком мало - исправляем:
# Для PPPoE:
/ip firewall mangle set [find comment~"MSS Clamping PPPoE"] new-mss=1452
# Или переключаемся на clamp-to-pmtu:
/ip firewall mangle set [find comment~"MSS"] new-mss=clamp-to-pmtu
Ошибка 4 - IPv6 HTTPS зависает, IPv4 работает
Симптом
После настройки MSS Clamping для IPv4 всё заработало. Но сайты с IPv6 продолжают зависать.
# Забыли про IPv6 mangle. Добавляем:
/ipv6 firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
action=change-mss \
new-mss=clamp-to-pmtu \
comment="MSS Clamping IPv6"
# Проверяем:
/ipv6 firewall mangle print stats
# Для IPv6 также нужно правило для output:
/ipv6 firewall mangle add \
chain=output \
protocol=tcp \
tcp-flags=syn \
action=change-mss \
new-mss=clamp-to-pmtu \
comment="MSS Clamping IPv6 output"
Ошибка 5 - Дублирующиеся правила MSS Clamping
Если несколько правил с одинаковым действием - они не сломают сеть, но создают лишнюю нагрузку и путаницу. Чистим.
# Смотрим все правила mangle:
/ip firewall mangle print
# Удаляем дубли (по номеру правила):
/ip firewall mangle remove numbers=3,4
# Или по комментарию - осторожно, удалит все совпадения:
/ip firewall mangle remove [find comment~"MSS Clamping"]
# После этого добавь правило заново - убедись что осталось одно нужное
Ошибка 6 - MSS Clamping ломает IPsec туннель
Симптом
После добавления MSS Clamping перестал работать site-to-site IPsec туннель или данные по туннелю передаются некорректно.
# IPsec-трафик нужно исключить из MSS Clamping или применять аккуратно.
# Проверяем политики IPsec:
/ip ipsec policy print
# Для site-to-site IPsec используй отдельное правило с фильтрацией по интерфейсу:
/ip firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
out-interface=!lo \
ipsec-policy=out,ipsec \
action=change-mss \
new-mss=1378 \
comment="MSS Clamping IPsec outbound"
/ip firewall mangle add \
chain=forward \
protocol=tcp \
tcp-flags=syn \
in-interface=!lo \
ipsec-policy=in,ipsec \
action=change-mss \
new-mss=1378 \
comment="MSS Clamping IPsec inbound"
Таблица портов и протоколов
| Протокол |
Порт |
Направление |
Зачем нужен для MSS |
| HTTPS |
TCP 443 |
Исходящий |
Основной затронутый протокол |
| HTTP |
TCP 80 |
Исходящий |
Менее чувствителен к MSS |
| ICMP Type 3 Code 4 |
- |
Входящий |
Fragmentation Needed - нужен для PMTUD |
| PPPoE Discovery |
ETH 0x8863/0x8864 |
Оба |
Добавляет 8 байт overhead к MTU |
| GRE |
IP proto 47 |
Оба |
24 байта overhead |
| IPsec ESP |
UDP 4500 / IP proto 50 |
Оба |
~50-80 байт overhead |
| WireGuard |
UDP 51820 |
Оба |
~80 байт overhead |
Когда MSS Clamping нужен, а когда нет
Настраивай обязательно:
- PPPoE-подключение к провайдеру (MTU 1492)
- L2TP, PPTP, GRE туннели
- IPsec (ESP) - site-to-site и road warrior
- WireGuard, OpenVPN
- LTE/4G/5G-подключения с нестандартным MTU
- Туннель внутри туннеля (каждый уровень добавляет overhead)
- Site-to-site VPN для объединения офисов
Не трогай:
- Обычное Ethernet-подключение без туннелей (MTU 1500, MSS 1460 - всё штатно)
- PMTUD работает корректно и ICMP не блокируется
- Медленная загрузка из-за DNS или proxy - диагностируй правильно
- MSS уже настроен провайдером на своём оборудовании
Безопасность при настройке MSS Clamping
MSS Clamping сам по себе безопасен - он работает только с SYN-пакетами при открытии соединения, не расшифровывает и не модифицирует данные.
Но пока открыт Firewall Mangle - проверь общее состояние безопасности:
# Проверяем что базовые правила firewall на месте:
/ip firewall filter print
# Должны быть правила:
# - accept established,related
# - drop invalid
# - accept input from LAN
# - drop input from WAN (кроме нужных портов)
# Проверяем что нет посторонних открытых правил:
/ip firewall filter print where action=accept chain=input
# Убеждаемся что Winbox доступен только из LAN, не из WAN:
/ip firewall filter print where dst-port=8291
Не делай это в продакшне без бэкапа
Перед изменениями в firewall mangle всегда делай бэкап конфигурации. Одна опечатка в правиле может заблокировать весь транзитный трафик.
Резервное копирование конфигурации MikroTik
# Бэкап перед изменениями (бинарный - всё включая пароли):
/system backup save name=before-mss-clamping
# Экспорт конфигурации в текст (читаемый, без паролей):
/export file=before-mss-clamping-export
# Скачай файлы через Winbox: Files - скачай .backup и .rsc
# Или через SCP:
# scp admin@192.168.88.1:before-mss-clamping.backup ./
# Восстановление из бэкапа если что-то сломалось:
/system backup load name=before-mss-clamping
Профилактика: как не сломать снова
- Документируй MTU каждого интерфейса - добавляй комментарий к правилу mangle с реальным MTU. Через год сам скажешь себе спасибо.
- Используй clamp-to-pmtu как дефолт - динамически подстраивается, не нужно пересчитывать при смене провайдера.
- Не блокируй ICMP Type 3 полностью - можешь блокировать echo-request (ping), но Destination Unreachable нужен для PMTUD. Правило в firewall filter: accept icmp where icmp-options=3:4.
- Проверяй MSS после смены провайдера - новый провайдер может иметь другой MTU.
- При добавлении нового туннеля - сразу пересчитывай MSS. Не "потом".
- Мониторь ICMP unreachable - рост таких сообщений сигнализирует о проблемах с PMTUD.
Обновление RouterOS с MSS Clamping
# Перед обновлением RouterOS:
# 1. Бэкап:
/system backup save name=pre-update-backup
# 2. Проверь changelog на изменения в firewall/mangle:
# https://mikrotik.com/download/changelogs
# 3. Обновляй в тестовой среде сначала если есть возможность
# После обновления:
# 4. Проверь что правила mangle на месте:
/ip firewall mangle print
# 5. Проверь счётчики:
/ip firewall mangle print stats
# 6. Функциональный тест HTTPS с клиентского ПК
Альтернативные решения
Вариант 1 - Уменьшить MTU интерфейса на MikroTik
Вместо MSS Clamping можно уменьшить MTU самого интерфейса. Тогда сетевой стек сам будет генерировать пакеты правильного размера.
# Уменьшаем MTU Ethernet-интерфейса:
/interface ethernet set ether1 mtu=1492
# Минус: влияет на весь трафик через интерфейс, не только TCP.
# MSS Clamping точечнее - работает только с SYN-пакетами.
Вариант 2 - Разрешить ICMP Type 3 Code 4 в firewall
Если PMTUD работает корректно - MSS Clamping не нужен. Убедись что ICMP Fragmentation Needed не блокируется.
# На MikroTik - разрешаем ICMP Fragmentation Needed:
/ip firewall filter add \
chain=input \
protocol=icmp \
icmp-options=3:4 \
action=accept \
comment="Allow ICMP Fragmentation Needed for PMTUD" \
place-before=0
# Это позволит PMTUD работать без MSS Clamping
Вариант 3 - ip tcp adjust-mss на Linux/iptables
# На Linux-роутере (iptables):
iptables -t mangle -A FORWARD -p tcp --tcp-flags SYN,RST SYN \
-j TCPMSS --clamp-mss-to-pmtu
# nftables (современный вариант):
nft add rule ip mangle FORWARD tcp flags syn / syn,rst \
tcp option maxseg size set rt mtu
# Сохраняем:
iptables-save > /etc/iptables/rules.v4
FAQ
Почему HTTPS не работает после подключения VPN, а HTTP работает нормально?
VPN-туннель добавляет свои заголовки к каждому пакету - это уменьшает реальный MTU канала. TLS ClientHello при HTTPS-рукопожатии передаётся с флагом Don't Fragment и имеет значительный размер. Если MTU канала уменьшился из-за VPN, а MSS не подстроен - ClientHello не проходит, и браузер зависает на соединении. Решение: настроить MSS Clamping на роутере или VPN-сервере.
Как проверить текущий MSS который анонсирует мой компьютер?
# Windows - через Wireshark или PowerShell:
# В Wireshark: tcp.flags.syn == 1 - смотри TCP Options -> Maximum segment size
# Linux - через ss или tcpdump:
ss -tin dst 8.8.8.8
# MikroTik - через torch или packet sniffer:
/tool sniffer start
/tool sniffer packet print
/tool sniffer stop
Что лучше - clamp-to-pmtu или фиксированное значение MSS?
Для большинства случаев clamp-to-pmtu предпочтительнее - он динамически определяет максимально допустимый MSS по MTU исходящего интерфейса, не требует ручного пересчёта и автоматически адаптируется при смене канала. Фиксированное значение оправдано когда clamp-to-pmtu определяет MTU неправильно (бывает на некоторых туннельных интерфейсах), или когда нужно гарантированно ограничить MSS конкретным значением независимо от интерфейса.
Нужно ли настраивать MSS Clamping если провайдер уже это делает?
Если провайдер настраивает MSS Clamping на своём оборудовании для PPPoE - твой роутер может не нуждаться в дополнительной настройке для самого PPPoE. Но если у тебя поверх PPPoE ещё VPN-туннель - добавляешь свой слой overhead, и правило нужно уже твоему роутеру. Диагностируй по факту: работает HTTPS нормально - не трогай.
Почему MSS Clamping не работает для уже установленных соединений?
MSS Clamping работает только с SYN-пакетами - теми, которые открывают новое TCP-соединение. Установившиеся сессии не затрагиваются: MSS согласован при рукопожатии и изменить его без разрыва соединения нельзя. Поэтому после добавления правила mangle уже активные соединения продолжат работу со старым MSS. Новые соединения получат правильный MSS сразу.
Какой MSS выставить для WireGuard?
WireGuard добавляет примерно 60-80 байт overhead в зависимости от конфигурации. Если внешний MTU 1500, то MTU WireGuard-интерфейса обычно 1420, MSS = 1380. Рекомендуется использовать clamp-to-pmtu - RouterOS сам определит MTU wg-интерфейса. Или явно задай MTU в настройках WireGuard-пира: /interface wireguard set wg0 mtu=1420.
Прогноз и итоги
Сделали следующее: разобрали механизм MSS от формулы до поведения TLS ClientHello, настроили MSS Clamping на MikroTik через mangle с clamp-to-pmtu, добавили IPv6, настроили Keenetic через веб и CLI, прошли через полный набор инструментов диагностики.
Теперь HTTPS-сессии будут открываться корректно через PPPoE, VPN и любые другие туннели. MSS Clamping - это не хак и не workaround, это стандартная практика для любой сети с инкапсуляцией. Если у тебя сеть с туннелями без MSS Clamping - это не "работает само", это "ещё не сломалось при определённых условиях".
Не заработало - разберёмся
Если после настройки HTTPS всё ещё виснет — пиши в комментарии. Опиши тип подключения, что показывает ping с флагом DF и счётчики mangle. Разберём конкретный случай.