gluon-alt-esc: add client + provider package

The client package allows to create a new wifi interface with direct access
to the local Freifunk network but with alternative exit gateways for internet
connectivity. A custom ESSID can be chosen.

The provider package is the counterpart to the client package and
configures the firewall of the selected Gluon node to grant permission to
route packets between the client and wan zone.

Note that the Gluon Alt-ESC provider package is not mandatory for the
Gluon Alt-ESC client package. In fact, any client device in the mesh network
can be chosen and configured to provide internet access for the Alt-ESC
client package.

Signed-off-by: Linus Lüssing <linus.luessing@c0d3.blue>
This commit is contained in:
Linus Lüssing 2018-11-15 02:10:03 +01:00
parent e56acfbec0
commit 3d6cd44629
20 changed files with 648 additions and 0 deletions

View File

@ -0,0 +1,41 @@
gluon-alt-esc-client
====================
The *gluon-alt-esc-client* package allows to create an additional wifi interface
with an alternative default gateway.
Accessibility
-------------
The alternative default gateway is configured by its MAC address in the config
mode. This host with its MAC needs to be a accessible directly within the mesh
network (client zone).
An easy way is to use the *gluon-alt-esc-provider* package and copy the
MAC address it presents in the config mode and paste it into the client
side configuration. However, the provider package is not mandatory - in fact
any host in the mesh network can potentially be chosen as an alternative default
gateway (as long as it allows routing, of course).
Only Off-link subnets are rerouted to the alternative exit. On-link subnets are
excluded. They are currently determined via *prefix4*, *prefix6*, *extra_prefixes4*
and *extra_prefixes6* from the site.conf.
Naming / ESSID
--------------
The name (so called ESSID) for the newly created wifi interface can be
freely chosen. However the author suggests to not use the word "Freifunk"
in it (for quite a while the internet is not a free/libre network anymore).
The following two hash tags are automatically appended:
*Zone-ID*: It prevents potential roaming conflicts. (Technically, it is generated
by taking the first four bytes of the hexadecimal form of an md5sum over
"<ipv4-gw-MAC>,<ipv6-gw-MAC>,<essid>")
*Site Code*: The communities site code is appended. To Freifunk enthusiasts it
signalizes:
- free and unaltered access to the Freifunk intranet of the local community
- that this node contributes to the local Freifunk community as a mesh node

View File

@ -0,0 +1,17 @@
gluon-alt-esc-provider
======================
The *gluon-alt-esc-provider* package is the counterpart to the *gluon-alt-esc-client*
package. It configures the firewall of the according Gluon node to grant permission
to route packets between the client (mesh clients) and wan zone (private network
behind the WAN port).
Packets from the client to the wan zone are NAT'ed both for IPv4 and IPv6.
Two notes: Beware of the security implications for routers and hosts in your wan
zone (yes, your 192.168.x.x devices will be accessible from the mesh).
Secondly, note that the Gluon Alt-ESC provider package is not mandatory for the
Gluon Alt-ESC client package. In fact, any client device in the mesh network
can be chosen and configured to provide internet access for the Alt-ESC
client package.

View File

@ -0,0 +1,16 @@
include $(TOPDIR)/rules.mk
PKG_NAME:=gluon-alt-esc-client
PKG_VERSION:=1
PKG_RELEASE:=1
include ../gluon.mk
define Package/gluon-alt-esc-client
DEPENDS:=+gluon-web-admin \
+@GLUON_SPECIALIZE_KERNEL:KERNEL_BRIDGE_EBT_DNAT \
+@GLUON_SPECIALIZE_KERNEL:KERNEL_BRIDGE_EBT_REDIRECT
TITLE:=Gluon Alternative Exit Service Collaborator - Client
endef
$(eval $(call BuildPackageGluon,gluon-alt-esc-client))

View File

@ -0,0 +1,5 @@
config client
option disabled '1'
option exit4 ''
option exit6 ''
option altesc_on_lan '0'

View File

@ -0,0 +1,86 @@
#!/bin/sh /etc/rc.common
. $IPKG_INSTROOT/usr/share/libubox/jshn.sh
START=60
sitejson="/lib/gluon/site.json"
__get_ifnames() {
local lanif
local altesc_on_lan=`uci get gluon-alt-esc-client.@client[0].altesc_on_lan`
for wifi in `uci show wireless | grep "wireless.altesc_radio.*\.ifname" | sed "s/\.ifname=.*//"`; do
[ "`uci get $wifi.disabled`" = 0 ] && \
uci get $wifi.ifname
done
[ "$altesc_on_lan" = "1" ] && cat /lib/gluon/core/sysconfig/lan_ifname
}
get_ifnames() {
ifnames=`__get_ifnames | sort`
}
setup_onlink_prefixes() {
json_load "$(cat /lib/gluon/site.json)"
json_get_var prefix4 prefix4
json_get_var prefix6 prefix6
json_get_values extra_prefixes4 extra_prefixes4
json_get_values extra_prefixes6 extra_prefixes6
if [ -n "$1" ]; then
M="$1"
OUT="2> /dev/null"
else
M="-I"
OUT=""
fi
for p4 in $prefix4 $extra_prefixes4; do
eval ebtables-tiny -t nat "$M" ALT_ESC_OFFLINK -p IPv4 --ip-dst $p4 -j RETURN $OUT
done
for p6 in $prefix6 $extra_prefixes6; do
eval ebtables-tiny -t nat "$M" ALT_ESC_OFFLINK -p IPv6 --ip6-dst $p6 -j RETURN $OUT
done
}
start() {
local exit4="`uci get gluon-alt-esc-client.@client[0].exit4 2> /dev/null | tr 'A-Z' 'a-z'`"
local exit6="`uci get gluon-alt-esc-client.@client[0].exit6 2> /dev/null | tr 'A-Z' 'a-z'`"
local ownmac="`uci get network.client.macaddr 2> /dev/null | tr 'A-Z' 'a-z'`"
local disabled="`uci get gluon-alt-esc-client.@client[0].disabled 2> /dev/null`"
get_ifnames
stop
[ ! "$disabled" = "0" ] && exit 0
for i in $ifnames; do
ebtables-tiny -t nat -A ALT_ESC -i $i --logical-in br-client -j ALT_ESC_OFFLINK
done
setup_onlink_prefixes
[ -n "$exit4" ] && {
if [ "$ownmac" = "$exit4" ]; then
ebtables-tiny -t nat -A ALT_ESC_DNAT -p IPv4 -j redirect --redirect-target ACCEPT
else
ebtables-tiny -t nat -A ALT_ESC_DNAT -p IPv4 -j dnat --to-dst "$exit4" --dnat-target ACCEPT
fi
}
[ -n "$exit6" ] && {
if [ "$ownmac" = "$exit6" ]; then
ebtables-tiny -t nat -A ALT_ESC_DNAT -p IPv6 -j redirect --redirect-target ACCEPT
else
ebtables-tiny -t nat -A ALT_ESC_DNAT -p IPv6 -j dnat --to-dst "$exit6" --dnat-target ACCEPT
fi
}
}
stop() {
ebtables-tiny -t nat -F ALT_ESC_DNAT
ebtables-tiny -t nat -F ALT_ESC
setup_onlink_prefixes "-D"
}

View File

@ -0,0 +1,4 @@
chain('ALT_ESC', 'ACCEPT', 'nat')
chain('ALT_ESC_OFFLINK', 'ACCEPT', 'nat')
chain('ALT_ESC_STDGW', 'RETURN', 'nat')
chain('ALT_ESC_DNAT', 'RETURN', 'nat')

View File

@ -0,0 +1,5 @@
rule ('PREROUTING -d Unicast -j ALT_ESC', 'nat')
rule ('ALT_ESC_OFFLINK -p IPv6 --ip6-src fe80::/ffc0:: -j RETURN', 'nat')
rule ('ALT_ESC_OFFLINK -p IPv4 --ip-dst 0.0.0.0 -j RETURN', 'nat')
rule ('ALT_ESC_OFFLINK -j ALT_ESC_STDGW', 'nat')

View File

@ -0,0 +1 @@
* * * * * nice /usr/sbin/altesc-update

View File

@ -0,0 +1,34 @@
#!/bin/sh
disabled=`uci get gluon-alt-esc-client.@client[0].disabled`
if [ ! "$disabled" = "0" ]; then
ebtables-tiny -t nat -F ALT_ESC_STDGW
exit 0
fi
get_gw_hosts() {
for gw in `batctl gwl -n -H | sed "s/.* \(..:..:..:..:..:..\) (.*/\1/"`; do
batctl tg -n -H | grep ".* ..:..:..:..:..:.. .* $gw"
done | sed "s/^.* \(..:..:..:..:..:..\) .* ..:..:..:..:..:.. .*/\1/" | sort
}
gwhosts="`get_gw_hosts`"
gwhostssum="`echo "$gwhosts" | md5sum`"
oldgwhosts="`cat /var/run/gluon-alt-esc.hosts 2> /dev/null`"
oldgwhostssum="`cat /var/run/gluon-alt-esc.hosts.md5sum 2> /dev/null`"
if [ "$gwhostssum" = "$oldgwhostssum" ]; then
echo "Stayed the same"
exit 0
fi
ebtables-tiny -t nat -F ALT_ESC_STDGW
for host in $gwhosts; do
ebtables-tiny -t nat -A ALT_ESC_STDGW -d "$host" -j ALT_ESC_DNAT
done
echo "$gwhosts" > /var/run/gluon-alt-esc.hosts
echo "$gwhostssum" > /var/run/gluon-alt-esc.hosts.md5sum

View File

@ -0,0 +1,58 @@
msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"PO-Revision-Date: 2017-11-13 08:00+0200\n"
"Last-Translator: Linus Lüssing <linus.luessing@c0d3.blue>\n"
"Language-Team: German\n"
"Language: de\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=2; plural=(n != 1);\n"
msgid ""
"Here you can add a WiFi interface with an alternative gateway for its "
"Internet connectivity. Usually, you connect to a node which has the "
"Alt-ESC-Provider package activated (although other systems can "
"provide access too)."
msgstr ""
"Hier kannst du ein WiFi Interface mit einem alternativen Gateway für "
"dessen Internetzugang hinzufügen. Normalerweise verbindest du dich mit "
"einem Knoten, welcher das Alt-ESC-Provider Paket aktiviert hat (wobei "
"auch andere Systeme Zugang bieten können)."
msgid "Name (SSID)"
msgstr "Name (SSID)"
msgid "Example: \"Lisa's Garden Gate\""
msgstr "Beispiel: \"Lisas Gartentor\""
msgid "Enable IPv4 redirection"
msgstr "Umleitung für IPv4 aktivieren"
msgid "Exit ID for IPv4"
msgstr "Exit ID für IPv4"
msgid "E.g. MAC address of the node serving as Alt-ESC-Provider for the IPv4 internet"
msgstr "Z.B. die MAC-Adresse eines Knoten, der als Alt-ESC-Provider für das IPv4 Internet dient"
msgid "Enable IPv6 redirection"
msgstr "Umleitung für IPv6 aktivieren"
msgid "Exit ID for IPv6"
msgstr "Exit ID für IPv6"
msgid "E.g. MAC address of the node serving as Alt-ESC-Provider for the IPv6 internet"
msgstr "Z.B. die MAC-Adresse eines Knoten, der als Alt-ESC-Provider für das IPv6 Internet dient"
msgid "Enable redirection on LAN ports"
msgstr "Umleitung auf LAN-Ports aktivieren"
msgid "Enable Password"
msgstr "Passwort aktivieren"
msgid "Password"
msgstr "Passwort"
msgid "8-63 characters. Note: No strict enforcement (yet)"
msgstr "8-63 Zeichen. Hinweis: (Bisweilen) keine strikte Durchsetzung"

View File

@ -0,0 +1,45 @@
msgid ""
msgstr "Content-Type: text/plain; charset=UTF-8"
msgid ""
"Here you can add a WiFi interface with an alternative gateway for its "
"Internet connectivity. Usually, you connect to a node which has the "
"Alt-ESC-Provider package activated (although other systems can "
"provide access too)."
msgstr ""
msgid "Name (SSID)"
msgstr ""
msgid "Example: \"Lisa's Garden Gate\""
msgstr ""
msgid "Enable IPv4 redirection"
msgstr ""
msgid "Exit ID for IPv4"
msgstr ""
msgid "E.g. MAC address of the node serving as Alt-ESC-Provider for the IPv4 internet"
msgstr ""
msgid "Enable IPv6 redirection"
msgstr ""
msgid "Exit ID for IPv6"
msgstr ""
msgid "E.g. MAC address of the node serving as Alt-ESC-Provider for the IPv6 internet"
msgstr ""
msgid "Enable redirection on LAN ports"
msgstr ""
msgid "Enable Password"
msgstr ""
msgid "Password"
msgstr ""
msgid "8-63 characters. Note: No strict enforcement (yet)"
msgstr ""

View File

@ -0,0 +1 @@
entry({"admin", "altesc-client"}, model("admin/altesc-client"), _("Alt-ESC Client"), 61)

View File

@ -0,0 +1,160 @@
local uci = require("simple-uci").cursor()
local util = require 'gluon.util'
local site = require 'gluon.site'
local hash = require 'hash'
local function get_client(uci)
local client
uci:foreach('gluon-alt-esc-client', 'client',
function(s)
client = s
return false
end
)
return client
end
local client = get_client(uci)['.name']
local disabled = uci:get_first('gluon-alt-esc-client', 'client', "disabled")
local site_code
if site.site_code then
sitecode = site.site_code()
else
sitecode = "ff"
end
-- reserve space for suffixes, SSID limited to 32 characters by standard
local ssidlen = 32 - string.len(" #abcd #" .. sitecode)
local ssiddata = uci:get('wireless', 'altesc_radio0', "ssid")
-- Remove sitecode suffix
if ssiddata and string.match(ssiddata, " #" .. sitecode .. "$") then
ssiddata = string.match(ssiddata, "^(.*) #" .. sitecode .. "$")
end
-- Remove zone suffix
if ssiddata and string.match(ssiddata, " #%x%x%x%x$") then
ssiddata = string.match(ssiddata, "^(.*) #%x%x%x%x$")
end
local f = Form(translate("Alternative Exit Service Collaborator - Client"))
local s = f:section(Section, nil, translate(
'Here you can add a WiFi interface with an alternative gateway for its '
.. 'Internet connectivity. Usually, you connect to a node which has the '
.. 'Alt-ESC-Provider package activated (although other systems can '
.. 'provide access too).'
))
local enabled = s:option(Flag, "enabled", translate("Enable"))
enabled.default = ssiddata and disabled and disabled == "0"
local ssid = s:option(Value, "ssid", translate("Name (SSID)"), translate('Example: "Lisa\'s Garden Gate"'))
ssid:depends(enabled, true)
ssid.datatype = "maxlength(" .. ssidlen .. ")"
ssid.default = ssiddata
local exit4data = uci:get_first('gluon-alt-esc-client', 'client', "exit4")
local exit4flag = s:option(Flag, "exit4flag", translate("Enable IPv4 redirection"))
exit4flag:depends(enabled, true)
exit4flag.default = (exit4data and exit4data ~= "")
local exit4 = s:option(Value, "exit4", translate("Exit ID for IPv4"), translate("E.g. MAC address of the node serving as Alt-ESC-Provider for the IPv4 internet"))
exit4:depends(exit4flag, true)
--exit4.datatype = "macaddr"
exit4.default = exit4data
local exit6data = uci:get_first('gluon-alt-esc-client', 'client', "exit6")
local exit6flag = s:option(Flag, "exit6flag", translate("Enable IPv6 redirection"))
exit6flag:depends(enabled, true)
exit6flag.default = (exit6data and exit6data ~= "")
local exit6 = s:option(Value, "exit6", translate("Exit ID for IPv6"), translate("E.g. MAC address of the node serving as Alt-ESC-Provider for the IPv6 internet"))
exit6:depends(exit6flag, true)
--exit6.datatype = "macaddr"
exit6.default = exit6data
local landata = uci:get_first('gluon-alt-esc-client', 'client', "altesc_on_lan")
local altesc_on_lan = s:option(Flag, "altesc_on_lan", translate("Enable redirection on LAN ports"))
altesc_on_lan:depends(enabled, true)
altesc_on_lan.default = landata and landata == '1'
local keydata = uci:get_first('gluon-alt-esc-client', 'client', "encryption")
local keyflag = s:option(Flag, "keyflag", translate("Enable Password"))
keyflag:depends(enabled, true)
keyflag.default = (keydata and keydata ~= "" and keydata ~= "none")
local key = s:option(Value, "key", translate("Password"), translate("8-63 characters. Note: No strict enforcement (yet)"))
key:depends(keyflag, true)
key.datatype = "wpakey"
key.default = uci:get_first('gluon-alt-esc-client', 'client', "key")
function f:write(self, state, data)
local client = get_client(uci)['.name']
uci:set('gluon-alt-esc-client', client, 'disabled', enabled.data and '0' or '1')
uci:set('gluon-alt-esc-client', client, 'exit4', exit4.data or '')
uci:set('gluon-alt-esc-client', client, 'exit6', exit6.data or '')
uci:set('gluon-alt-esc-client', client, 'altesc_on_lan', altesc_on_lan.data and '1' or '0')
uci:commit('gluon-alt-esc-client')
i=0
util.foreach_radio(uci,
function(radio, index, config)
local name = "altesc_" .. radio['.name']
if enabled.data then
local macaddr = util.get_wlan_mac(uci, radio, index, 4)
local exit4data = exit4.data or ""
local exit6data = exit4.data or ""
local sitecode
local zone = string.sub(hash.md5(exit4data .. "," .. exit6data .. "," .. ssid.data), 0, 4)
if site.site_code then
sitecode = site.site_code()
else
sitecode = "ff"
end
if keyflag.data and key.data then
uci:section('wireless', "wifi-iface", name,
{
ifname = "altesc" .. i,
device = radio['.name'],
network = "client",
mode = "ap",
macaddr = macaddr,
ssid = ssid.data .. " #" .. zone .. " #" .. sitecode,
encryption = "psk2",
key = key.data,
disabled = '0',
}
)
else
uci:section('wireless', "wifi-iface", name,
{
ifname = "altesc" .. i,
device = radio['.name'],
network = "client",
mode = "ap",
macaddr = macaddr,
ssid = ssid.data .. " #" .. zone .. " #" .. sitecode,
encryption = "",
key = "",
disabled = '0',
}
)
end
else
uci:set('wireless', name, "disabled", 1)
end
i=i+1
end
)
uci:commit('wireless')
end
return f

View File

@ -0,0 +1,14 @@
include $(TOPDIR)/rules.mk
PKG_NAME:=gluon-alt-esc-provider
PKG_VERSION:=1
PKG_RELEASE:=1
include ../gluon.mk
define Package/gluon-alt-esc-provider
DEPENDS:=+gluon-web-admin +ip6tables-mod-nat
TITLE:=Gluon Alternative Exit Service Collaborator - Provider
endef
$(eval $(call BuildPackageGluon,gluon-alt-esc-provider))

View File

@ -0,0 +1,2 @@
config provider
option disabled '1'

View File

@ -0,0 +1,3 @@
*nat
-I POSTROUTING -o br-wan -j MASQUERADE
COMMIT

View File

@ -0,0 +1,42 @@
msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"PO-Revision-Date: 2017-11-13 08:00+0200\n"
"Last-Translator: Linus Lüssing <linus.luessing@c0d3.blue>\n"
"Language-Team: German\n"
"Language: de\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=2; plural=(n != 1);\n"
msgid ""
"<p>Here you can share your Internet connection from the WAN port directly "
"(bypassing the community gateways), so this same or other nodes can "
"get Internet access via this node via the Alt-ESC-Client, for instance.</p>"
"<p><strong>- Be aware of the legal obligations your jurisdiction might "
"require you to follow. -</strong></p>"
"<p><strong>USE AT YOUR OWN RISK!</strong></p>"
msgstr ""
"<p>Hier kannst deine Internetverbindung vom WAN-Port direkt teilen "
"(dies umgeht den Community-Gateway), sodass dieser oder andere "
"Knoten einen Internetzugang über diesen Knoten zum Beispiel durch den "
"Alt-ESC-Client bekommen können.</p>"
"<p><strong>- Sei dir über die gesetzlichen Verpflichtungen bewusst, deren "
"Befolgung dein Rechtssystem möglichrweise vorschreibt. -</strong></p>"
"<p><strong>BENUTZUNG AUF EIGENE GEFAHR!</strong></p>"
msgid "Enable"
msgstr "Aktivieren"
msgid "Note: When enabling this you will probably want to enable the Mesh-VPN in the wizard, too."
msgstr "Anmerkung: Wenn du dies aktivierst, willst du vermutlich auch das Mesh-VPN im Wizard aktivieren."
msgid "I am brave and I know what I am doing."
msgstr "Ich bin mutig und weiß was ich tue."
msgid "Your Exit ID is:"
msgstr "Deine Exit ID ist:"
msgid "(unchangeable, your nodes MAC address)"
msgstr "(unveränderlich, die MAC Adresse deines Knotens)"

View File

@ -0,0 +1,26 @@
msgid ""
msgstr "Content-Type: text/plain; charset=UTF-8"
msgid ""
"<p>Here you can share your Internet connection from the WAN port directly "
"(bypassing the community gateways), so this same or other nodes can "
"get Internet access via this node via the Alt-ESC-Client, for instance.</p>"
"<p><strong>- Be aware of the legal obligations your jurisdiction might "
"require you to follow. -</strong></p>"
"<p><strong>USE AT YOUR OWN RISK!</strong></p>"
msgstr ""
msgid "Enable"
msgstr ""
msgid "Note: When enabling this you will probably want to enable the Mesh-VPN in the wizard, too."
msgstr ""
msgid "I am brave and I know what I am doing."
msgstr ""
msgid "Your Exit ID is:"
msgstr ""
msgid "(unchangeable, your nodes MAC address)"
msgstr ""

View File

@ -0,0 +1 @@
entry({"admin", "altesc-provider"}, model("admin/altesc-provider"), _("Alt-ESC Provider"), 60)

View File

@ -0,0 +1,87 @@
local uci = require("simple-uci").cursor()
local util = require 'gluon.util'
local site = require 'gluon.site'
local function get_provider(uci)
local provider
uci:foreach('gluon-alt-esc-provider', 'provider',
function(s)
provider = s
return false
end
)
return provider
end
local mac = uci:get('network', 'client', 'macaddr')
local disabled = uci:get_first('gluon-alt-esc-provider', 'provider', "disabled")
local f = Form(translate("Alternative Exit Service Collaborator - Provider"))
local s = f:section(Section, nil, translate(
'<p>Here you can share your Internet connection from the WAN port directly '
.. '(bypassing the community gateways), so this same or other nodes can '
.. 'get Internet access via this node via the Alt-ESC-Client, for instance.</p>'
.. '<p><strong>- Be aware of the legal obligations your jurisdiction might '
.. 'require you to follow. -</strong></p>'
.. '<p><strong>USE AT YOUR OWN RISK!</strong></p>'
))
local enabled = s:option(Flag, "enabled", translate("Enable"), translate("Note: When enabling this you will probably want to enable the Mesh-VPN in the wizard, too."))
enabled.default = disabled and disabled == "0"
local brave = s:option(Flag, "brave", translate("I am brave and I know what I am doing."))
brave:depends(enabled, true)
brave.default = disabled and disabled == "0"
local id = s:option(Value, "id", translate("Your Exit ID is:"), translate("(unchangeable, your nodes MAC address)"))
id:depends(brave, true)
id.default = mac
function f:write(self, state, data)
local disabled
local provider = get_provider(uci)['.name']
if not(enabled.data and brave.data) then
disabled = "1"
uci:delete('firewall', 'client2wan')
uci:delete('firewall', 'wan2client')
uci:delete('firewall', 'wan_nat6')
uci:delete('network', 'wan6client_lookup')
else
disabled = "0"
uci:section('firewall', 'forwarding', 'client2wan',
{
src = 'mesh',
dest = 'wan',
}
)
uci:section('firewall', 'forwarding', 'wan2client',
{
src = 'wan',
dest = 'mesh',
}
)
uci:section('firewall', 'include', 'wan_nat6',
{
family = 'ipv6',
type = 'restore',
path = '/lib/gluon/alt-esc-provider/iptables.rules',
}
)
uci:section('network', 'rule6', 'wan6client_lookup',
{
lookup = '1',
}
)
uci:set('network', 'wan6client_lookup', 'in', 'client')
end
uci:set('gluon-alt-esc-provider', provider, 'disabled', disabled)
uci:commit('gluon-alt-esc-provider')
uci:commit('firewall')
uci:commit('network')
end
return f