Bug #16664
openAdvLinkMTU hardcoded to 1500 despite 6rd interface
0%
Description
I originally opened this as a feature request https://redmine.pfsense.org/issues/16659. After further consideration, I think this falls into the bug category. When users configure 6rd on a WAN interface, the primary goal is to deliver functional IPv6 connectivity to LAN hosts. However, pfSense currently configures radvd to advertise AdvLinkMTU 1500 by default, matching the standard Ethernet interface MTU even though the 6rd tunnel reduces the effective IPv6 path MTU to 1480 due to IPv4 encapsulation overhead.
This default advertisement of 1500 actively invites MTU related breakage. LAN clients (particularly Windows systems) ignore the ICMPv6 Packet Too Big messages which are notoriously unreliable in real-world deployments. Many clients ignore or inconsistently process PTB messages, leading to persistent connectivity issues. e.g. unable to reach https://learning.microsoft.com
The current behavior undermines the expected functionality of 6rd deployments, and the only workaround, forcing the entire interface MTU down to 1480, unnecessarily penalizes IPv4 performance. Allowing AdvLinkMTU to be configured independently (or automatically detecting/adjusting for tunnel interfaces) is necessary to avoid broken IPv6 connectivity.
Per RFC 4861:
The MTU option is used in Router Advertisement
messages to ensure that all nodes on a link use the
same MTU value in those cases where the link MTU is not well known.
An MTU of 1500 is well-known . Setting AdvLinkMTU to the well-known MTU of 1500 not only isn't needed, it's inviting broken connectivity.
For anyone experiencing this issue in the meantime, your options are to either set ALL LAN traffic to 1480 by configuring the LAN interface MTU to 1480, or you can use the hack below to configure AdvLinkMTU with the proper value which only affects IPv6 traffic.
This is known to work on pfSense plus version 25.11-RELEASE
Modify /etc/inc/services.inc
From this:
$mtu = get_interface_mtu($realif);
if (is_numeric($mtu)) {
$radvdconf .= "\tAdvLinkMTU {$mtu};\n";
} else {
$radvdconf .= "\tAdvLinkMTU 1280;\n";
}
to this:
$mtu = get_interface_mtu($realif);
if (is_numeric($mtu)) {
$radvdconf .= "\tAdvLinkMTU 1480;\n";
} else {
$radvdconf .= "\tAdvLinkMTU 1280;\n";
}
No data to display