luci-mod-network: check kernel for mptcp to display MPTCP options

https://www.kernel.org/doc/html/v6.12/networking/mptcp-sysctl.html

There may be user instances where mptcp was not compiled
into the kernel or is an unloaded module, so gate the options
behind the feature check.

Closes #8522

Signed-off-by: Paul Donald <newtwen+github@gmail.com>
This commit is contained in:
Paul Donald
2026-04-04 19:12:54 +02:00
parent 9cccae92ee
commit a6b7ad4652
2 changed files with 15 additions and 10 deletions

View File

@@ -242,6 +242,7 @@ const methods = {
ufpd: access('/usr/sbin/ufpd') == true, ufpd: access('/usr/sbin/ufpd') == true,
vrf: access('/sys/module/vrf/refcnt') == true, // vrf.ko is loaded vrf: access('/sys/module/vrf/refcnt') == true, // vrf.ko is loaded
netifd_vrf: false, netifd_vrf: false,
mptcp: access('/proc/sys/net/mptcp/enabled'),
}; };
const wifi_features = [ const wifi_features = [

View File

@@ -1216,14 +1216,16 @@ return view.extend({
o.datatype = 'uinteger'; o.datatype = 'uinteger';
o.placeholder = '0'; o.placeholder = '0';
o = nettools.replaceOption(s, 'advanced', form.RichListValue, 'multipath', _('Multi-Path TCP'), if (L.hasSystemFeature('mptcp')) {
_('Multi-Path TCP') + ' %s'.format('<a href="%s" target="_blank">RFC8684</a>').format('https://www.rfc-editor.org/rfc/rfc8684.html') + '<br/>' + o = nettools.replaceOption(s, 'advanced', form.RichListValue, 'multipath', _('Multi-Path TCP'),
_('For packets originating from this device, e.g. VPN.') ); _('Multi-Path TCP') + ' %s'.format('<a href="%s" target="_blank">RFC8684</a>').format('https://www.rfc-editor.org/rfc/rfc8684.html') + '<br/>' +
o.value('off', _('Off'), _('Disables this interface for MPTCP')); _('For packets originating from this device, e.g. VPN.') );
o.value('on', _('On'), _('No special configuration')); o.value('off', _('Off'), _('Disables this interface for MPTCP'));
o.value('master', _('Master'), _('Sets default route for all traffic')); o.value('on', _('On'), _('No special configuration'));
o.value('backup', _('Backup'), _('Hot standby; use this interface; do not forward traffic until no other interface is available (faster)')); o.value('master', _('Master'), _('Sets default route for all traffic'));
o.value('handover', _('Handover'), _('Cold standby; Establish a connection only when no other interface is available (slower)')); o.value('backup', _('Backup'), _('Hot standby; use this interface; do not forward traffic until no other interface is available (faster)'));
o.value('handover', _('Handover'), _('Cold standby; Establish a connection only when no other interface is available (slower)'));
}
o = nettools.replaceOption(s, 'advanced', form.Value, 'ip4table', _('Override IPv4 routing table')); o = nettools.replaceOption(s, 'advanced', form.Value, 'ip4table', _('Override IPv4 routing table'));
o.datatype = 'or(uinteger, string)'; o.datatype = 'or(uinteger, string)';
@@ -1774,8 +1776,10 @@ return view.extend({
_('This identifier is randomly generated the first time the device is booted.')); _('This identifier is randomly generated the first time the device is booted.'));
o.datatype = 'and(rangelength(6,260),hexstring)'; o.datatype = 'and(rangelength(6,260),hexstring)';
o = s.option(form.Flag, 'multipath', _('Multi-Path TCP'), _('For packets originating from this device, e.g. VPN.')); if (L.hasSystemFeature('mptcp')) {
o.optional = true; o = s.option(form.Flag, 'multipath', _('Multi-Path TCP'), _('For packets originating from this device, e.g. VPN.'));
o.optional = true;
}
const l3mdevhelp1 = _('%s services running on this device in the default VRF context (ie., not bound to any VRF device) shall work across all VRF domains.'); const l3mdevhelp1 = _('%s services running on this device in the default VRF context (ie., not bound to any VRF device) shall work across all VRF domains.');
const l3mdevhelp2 = _('Off means VRF traffic will be handled exclusively by sockets bound to VRFs.'); const l3mdevhelp2 = _('Off means VRF traffic will be handled exclusively by sockets bound to VRFs.');