Backported UCI-Dependency Tracking and Responsiveness Improvements

This commit is contained in:
Steven Barth 2008-09-07 14:17:29 +00:00
parent 0d12944af5
commit 37b79596bb
27 changed files with 305 additions and 148 deletions

View file

@ -1,4 +1,7 @@
#!/bin/sh
uci set luci.uci_oncommit.luci_statistics='/etc/init.d/luci_statistics restart'
uci commit luci
uci batch <<-EOF
add ucitrack luci_statistics
set ucitrack.@luci_statistics[-1].init=luci_statistics
commit ucitrack
EOF

View file

@ -1,4 +1,7 @@
#!/bin/sh
uci set luci.uci_oncommit.uvc_streamer='/sbin/luci-reload uvc-streamer'
uci commit luci
uci batch <<-EOF
add ucitrack uvc-streamer
set ucitrack.@uvc-streamer[-1].init=uvc-streamer
commit ucitrack
EOF

View file

@ -30,7 +30,6 @@ define Package/luci-addons/install
$(INSTALL_BIN) ./dist/usr/bin/run-parts $(1)/usr/bin
$(INSTALL_BIN) ./dist/sbin/luci-flash $(1)/sbin
$(INSTALL_BIN) ./dist/sbin/luci-reload $(1)/sbin
$(INSTALL_BIN) ./dist/etc/init.d/luci_fixtime $(1)/etc/init.d
$(INSTALL_BIN) ./dist/etc/init.d/luci_ethers $(1)/etc/init.d
$(INSTALL_BIN) ./dist/etc/init.d/luci_hosts $(1)/etc/init.d

View file

@ -85,5 +85,9 @@ done
[ -n "$sysupgrade_init_conffiles" ] && do_save_conffiles
run_hooks "" $sysupgrade_pre_upgrade
ask_bool() {
false
}
v "Switching to ramdisk..."
run_ramfs '. /etc/functions.sh; include /lib/upgrade; do_upgrade'

View file

@ -1,9 +0,0 @@
#!/bin/sh
for i in $*
do
[ -x /etc/init.d/$i ] && {
echo -n "Reloading $i... "
/etc/init.d/$i restart >/dev/null 2>&1 && echo "done." || echo "failed!"
}
done

View file

@ -69,6 +69,8 @@ a_s_fstab_swap1 = 'If your physical memory is insufficient unused data can be te
a_s_flash_flashed = 'Firmware successfully flashed. Rebooting device...'
a_s_flash_flasherr = 'Failed to flash'
a_s_flash_fwimage = 'Firmwareimage'
a_s_flash_received = 'Image received. About to start flashing process. DO NOT POWER OFF THE DEVICE!'
a_s_flash_inprogress = 'Writing firmware...'
a_s_flash_fwupgrade = 'Flash Firmware'
a_s_flash_keepcfg = 'Keep configuration files'
a_s_flash_notimplemented = 'Sorry, this function is not (yet) available for your platform.'

View file

@ -73,6 +73,8 @@
<i18n:msg xml:id="a_s_flash_flashed">Firmware successfully flashed. Rebooting device...</i18n:msg>
<i18n:msg xml:id="a_s_flash_flasherr">Failed to flash</i18n:msg>
<i18n:msg xml:id="a_s_flash_fwimage">Firmwareimage</i18n:msg>
<i18n:msg xml:id="a_s_flash_received">Image received. About to start flashing process. DO NOT POWER OFF THE DEVICE!</i18n:msg>
<i18n:msg xml:id="a_s_flash_inprogress">Writing firmware...</i18n:msg>
<i18n:msg xml:id="a_s_flash_fwupgrade">Flash Firmware</i18n:msg>
<i18n:msg xml:id="a_s_flash_keepcfg">Keep configuration files</i18n:msg>
<i18n:msg xml:id="a_s_flash_notimplemented">Sorry, this function is not (yet) available for your platform.</i18n:msg>

View file

@ -11,3 +11,4 @@ cbi_sectempty = 'This section contains no values yet'
cbi_manual = '-- custom --'
cbi_select = '-- Please choose --'
cbi_gorel = 'Go to relevant configuration page'
cbi_applying = 'Applying changes'

View file

@ -15,5 +15,6 @@
<i18n:msg xml:id="cbi_manual">-- custom --</i18n:msg>
<i18n:msg xml:id="cbi_select">-- Please choose --</i18n:msg>
<i18n:msg xml:id="cbi_gorel">Go to relevant configuration page</i18n:msg>
<i18n:msg xml:id="cbi_applying">Applying changes</i18n:msg>
</i18n:msgs>

View file

@ -39,6 +39,8 @@ a_s_flash = 'Upgrade'
a_s_flash_flashed = 'Flashvorgang erfolgreich. Router startet neu...'
a_s_flash_flasherr = 'Flashvorgang fehlgeschlagen'
a_s_flash_fwimage = 'Firmwareimage'
a_s_flash_received = 'Abbild empfangen. Starte Flashvorgang. SCHALTEN SIE DAS GERÄT NICHT AUS!'
a_s_flash_inprogress = 'Schreibe Firmware...'
a_s_flash_fwupgrade = 'Firmware aktualisieren'
a_s_flash_keepcfg = 'Konfigurationsdateien übernehmen'
a_s_flash_notimplemented = 'Diese Funktion steht leider (noch) nicht zur Verfügung.'

View file

@ -43,6 +43,8 @@
<i18n:msg xml:id="a_s_flash_flashed">Flashvorgang erfolgreich. Router startet neu...</i18n:msg>
<i18n:msg xml:id="a_s_flash_flasherr">Flashvorgang fehlgeschlagen</i18n:msg>
<i18n:msg xml:id="a_s_flash_fwimage">Firmwareimage</i18n:msg>
<i18n:msg xml:id="a_s_flash_received">Abbild empfangen. Starte Flashvorgang. SCHALTEN SIE DAS GERÄT NICHT AUS!</i18n:msg>
<i18n:msg xml:id="a_s_flash_inprogress">Schreibe Firmware...</i18n:msg>
<i18n:msg xml:id="a_s_flash_fwupgrade">Firmware aktualisieren</i18n:msg>
<i18n:msg xml:id="a_s_flash_keepcfg">Konfigurationsdateien übernehmen</i18n:msg>
<i18n:msg xml:id="a_s_flash_notimplemented">Diese Funktion steht leider (noch) nicht zur Verfügung.</i18n:msg>

View file

@ -10,3 +10,4 @@ cbi_sectempty = 'Diese Sektion enthält noch keine Einträge'
cbi_manual = '-- benutzerdefiniert --'
cbi_select = '-- Bitte auswählen --'
cbi_gorel = 'Gehe zu relevanter Konfigurationsseite'
cbi_applying = 'Änderungen werden angewandt'

View file

@ -14,4 +14,6 @@
<i18n:msg xml:id="cbi_manual">-- benutzerdefiniert --</i18n:msg>
<i18n:msg xml:id="cbi_select">-- Bitte auswählen --</i18n:msg>
<i18n:msg xml:id="cbi_gorel">Gehe zu relevanter Konfigurationsseite</i18n:msg>
<i18n:msg xml:id="cbi_applying">Änderungen werden angewandt</i18n:msg>
</i18n:msgs>

View file

@ -221,6 +221,7 @@ function Map.__init__(self, config, ...)
self.config = config
self.parsechain = {self.config}
self.template = "cbi/map"
self.apply_on_parse = nil
self.uci = uci.cursor()
self.save = true
if not self.uci:load(self.config) then
@ -258,11 +259,18 @@ function Map.parse(self, ...)
if luci.http.formvalue("cbi.apply") then
for i, config in ipairs(self.parsechain) do
self.uci:commit(config)
self.uci:apply(config)
-- Refresh data because commit changes section names
self.uci:load(config)
end
if self.apply_on_parse then
self.uci:apply(self.parsechain)
else
self._apply = function()
local cmd = self.uci:apply(self.parsechain, true)
return io.popen(cmd)
end
end
-- Reparse sections
Node.parse(self, ...)
@ -274,6 +282,15 @@ function Map.parse(self, ...)
end
end
function Map.render(self, ...)
Node.render(self, ...)
if self._apply then
local fp = self._apply()
fp:read("*a")
fp:close()
end
end
-- Creates a child section
function Map.section(self, class, ...)
if instanceof(class, AbstractSection) then

View file

@ -16,6 +16,19 @@ $Id$
<div class="cbi-map" id="cbi-<%=self.config%>">
<h1><%=self.title%></h1>
<div class="cbi-map-descr"><%=self.description%></div>
<%- if self._apply then -%><code><%:cbi_applying%>:
<%
local fp = self._apply()
self._apply = nil
local line = fp:read()
while line do
write(line.."\n")
line = fp:read()
end
fp:close()
-%>
</code><%- end -%>
<%- self:render_children() %>
<br />
</div>

View file

@ -54,14 +54,17 @@ end
local Cursor = getmetatable(cursor())
--- Applies the new config
-- @param config UCI config
function Cursor.apply(self, config)
local conf = require "luci.config"
return conf.uci_oncommit[config] and
os.execute(conf.uci_oncommit[config] .. " >/dev/null 2>&1")
--- Applies UCI configuration changes
-- @param configlist List of UCI configurations
-- @param command Don't apply only return the command
function Cursor.apply(self, configlist, command)
configlist = self:_affected(configlist)
local reloadcmd = "/sbin/luci-reload " .. table.concat(configlist, " ")
return command and reloadcmd or os.execute(reloadcmd .. " >/dev/null 2>&1")
end
--- Delete all sections of a given type that match certain criteria.
-- @param config UCI config
-- @param type UCI section type
@ -180,6 +183,51 @@ function Cursor.changes(self, config)
end
-- Return a list of initscripts affected by configuration changes.
function Cursor._affected(self, configlist)
configlist = type(configlist) == "table" and configlist or {configlist}
local c = cursor()
c:load("ucitrack")
-- Resolve dependencies
local reloadlist = {}
local function _resolve_deps(name)
local reload = {name}
local deps = {}
c:foreach("ucitrack", name,
function(section)
if section.affects then
for i, aff in ipairs(section.affects) do
table.insert(deps, aff)
end
end
end)
for i, dep in ipairs(deps) do
for j, add in ipairs(_resolve_deps(dep)) do
table.insert(reload, add)
end
end
return reload
end
-- Collect initscripts
for j, config in ipairs(configlist) do
for i, e in ipairs(_resolve_deps(config)) do
if not util.contains(reloadlist, e) then
table.insert(reloadlist, e)
end
end
end
return reloadlist
end
--- Add an anonymous section.
-- @class function
-- @name Cursor.add

View file

@ -0,0 +1,50 @@
config network
option init network
list affects dhcp
config wireless
list affects network
config firewall
option init firewall
list affects luci-splash
list affects qos
config olsr
option init olsrd
config dhcp
option init dnsmasq
config dropbear
option init dropbear
config httpd
option init httpd
config fstab
option init fstab
config qos
option init qos
config system
option init led
config luci_ethers
option init luci_ethers
config luci_hosts
option init luci_hosts
config luci_splash
option init luci_splash
config upnpd
option init miniupnpd
config ntpclient
option init ntpclient
config samba
option init samba

32
libs/uci/root/sbin/luci-reload Executable file
View file

@ -0,0 +1,32 @@
#!/bin/sh
. /etc/functions.sh
apply_config() {
config_get init "$1" init
config_get exec "$1" exec
[ -n "$init" ] && reload_init "$2" "$init"
[ -n "$exec" ] && reload_exec "$2" "$exec"
}
reload_exec() {
[ -x $2 ] && {
echo "Reloading $1... "
$2 >/dev/null 2>&1 || echo "!!! Failed to reload $1 !!!"
}
}
reload_init() {
[ -x /etc/init.d/$2 ] && /etc/init.d/$2 enabled && {
echo "Reloading $1... "
/etc/init.d/$2 reload >/dev/null 2>&1 || echo "!!! Failed to reload $1 !!!"
}
}
config_load ucitrack
for i in $*
do
config_foreach apply_config $i $i
echo "done."
done

View file

@ -18,24 +18,6 @@ config extern flash_keep
option httpd "/etc/httpd.conf"
option firewall "/etc/firewall.user"
config event uci_oncommit
option network "/sbin/luci-reload network firewall dnsmasq luci_splash"
option wireless "/sbin/luci-reload network firewall dnsmasq luci_splash"
option olsr "/sbin/luci-reload olsrd"
option dhcp "/sbin/luci-reload dnsmasq"
option dropbear "/sbin/luci-reload dropbear"
option httpd "/sbin/luci-reload httpd"
option fstab "/sbin/luci-reload fstab"
option qos "/sbin/luci-reload qos"
option system "/sbin/luci-reload led"
option firewall "/sbin/luci-reload firewall luci_splash"
option luci_hosts "/sbin/luci-reload luci_hosts dnsmasq"
option luci_ethers "/sbin/luci-reload luci_ethers dnsmasq"
option luci_splash "/sbin/luci-reload firewall luci_splash"
option upnpd "/etc/init.d/miniupnpd enabled && /sbin/luci-reload miniupnpd || /etc/init.d/miniupnpd stop"
option ntpclient "/sbin/luci-reload ntpclient"
option samba "/sbin/luci-reload samba"
config internal languages
config internal sauth

View file

@ -182,7 +182,7 @@ end
function action_upgrade()
require("luci.model.uci")
local ret = nil
local ret
local plat = luci.fs.mtime("/lib/upgrade/platform.sh")
local tmpfile = "/tmp/firmware.img"
local broadcom = os.execute('grep brcm_ /lib/upgrade/platform.sh >/dev/null 2>&1') == 0
@ -208,7 +208,9 @@ function action_upgrade()
local keepcfg = keep_avail and luci.http.formvalue("keepcfg")
if plat and fname then
ret = luci.sys.flash(tmpfile, keepcfg and _keep_pattern())
ret = function()
return luci.sys.flash(tmpfile, keepcfg and _keep_pattern())
end
end
luci.template.render("admin_system/upgrade", {sysupgrade=plat, ret=ret, keep_avail=keep_avail})
@ -224,4 +226,4 @@ function _keep_pattern()
end
end
return kpattern
end
end

View file

@ -24,27 +24,23 @@ function index()
end
function convert_changes(changes)
local ret = {}
local util = require "luci.util"
local ret
for r, tbl in pairs(changes) do
for s, os in pairs(tbl) do
for o, v in pairs(os) do
local val, str
if (v == "") then
str = "-"
val = ""
else
str = ""
val = "="..luci.util.pcdata(v)
end
str = r.."."..s
if o ~= ".type" then
str = str.."."..o
end
table.insert(ret, str..val)
ret = (ret and ret.."\n" or "") .. "%s%s.%s%s%s" % {
v == "" and "-" or "",
r,
s,
o ~= ".type" and "."..o or "",
v ~= "" and "="..util.pcdata(v) or ""
}
end
end
end
return table.concat(ret, "\n")
return ret
end
function action_changes()
@ -54,52 +50,38 @@ end
function action_apply()
local path = luci.dispatcher.context.path
local output = ""
local uci = luci.model.uci.cursor()
local changes = uci:changes()
if changes then
local com = {}
local run = {}
-- Collect files to be applied and commit changes
for r, tbl in pairs(changes) do
if r then
if path[#path] ~= "apply" then
uci:load(r)
uci:commit(r)
uci:unload(r)
end
if luci.config.uci_oncommit and luci.config.uci_oncommit[r] then
run[luci.config.uci_oncommit[r]] = true
end
end
end
-- Search for post-commit commands
for cmd, i in pairs(run) do
output = output .. cmd .. ":\n" .. luci.util.exec(cmd) .. "\n"
local reload = {}
-- Collect files to be applied and commit changes
for r, tbl in pairs(changes) do
table.insert(reload, r)
if path[#path] ~= "apply" then
uci:load(r)
uci:commit(r)
uci:unload(r)
end
end
local function _reload()
local cmd = uci:apply(reload, true)
return io.popen(cmd)
end
luci.template.render("admin_uci/apply", {changes=convert_changes(changes), output=output})
luci.template.render("admin_uci/apply", {changes=convert_changes(changes), reload=_reload})
end
function action_revert()
local uci = luci.model.uci.cursor()
local changes = uci:changes()
if changes then
local revert = {}
-- Collect files to be reverted
for r, tbl in pairs(changes) do
uci:load(r)
uci:revert(r)
uci:unload(r)
end
-- Collect files to be reverted
for r, tbl in pairs(changes) do
uci:load(r)
uci:revert(r)
uci:unload(r)
end
luci.template.render("admin_uci/revert", {changes=convert_changes(changes)})

View file

@ -34,7 +34,13 @@ $Id$
</div>
</form>
<% elseif ret then %>
<% if ret == 0 then %>
<p><%:a_s_flash_received%></p>
<p><%:a_s_flash_inprogress%></p>
<!-- <%=string.rep(" ", 2048)%> -->
<% %>
<% local ret = ret()
if ret == 0 then %>
<div class="ok"><%:a_s_flash_flashed%></div>
<% else %>
<div class="error"><%:a_s_flash_flasherr%>! (<%:code%> <%=ret%>)</div>
@ -42,4 +48,5 @@ $Id$
<% else %>
<div class="error"><%:a_s_flash_notimplemented%></div>
<% end %>
<%+footer%>
<%+footer%>
<% if ret == 0 then luci.sys.reboot() end %>

View file

@ -16,5 +16,14 @@ $Id$
<h1><%:config%></h1>
<p><%:uci_applied%>:</p>
<code><%=(changes or "-")%>
<%=output%></code>
<%
local fp = reload()
local line = fp:read()
while line do
write(line.."\n")
line = fp:read()
end
fp:close()
%></code>
<%+footer%>

View file

@ -105,7 +105,9 @@ function action_upgrade()
local keepcfg = keep_avail and luci.http.formvalue("keepcfg")
if plat and fname then
ret = luci.sys.flash(tmpfile, keepcfg and _keep_pattern())
ret = function()
return luci.sys.flash(tmpfile, keepcfg and _keep_pattern())
end
end
luci.template.render("mini/upgrade", {sysupgrade=plat, ret=ret, keep_avail=keep_avail})
@ -121,4 +123,4 @@ function _keep_pattern()
end
end
return kpattern
end
end

View file

@ -20,31 +20,27 @@ function index()
entry({"mini", "uci"}, nil, i18n("config"))
entry({"mini", "uci", "changes"}, call("action_changes"), i18n("changes"), 30)
entry({"mini", "uci", "revert"}, call("action_revert"), i18n("revert"), 20)
entry({"mini", "uci", "apply"}, call("action_apply"), i18n("saveapply"), 10)
entry({"mini", "uci", "saveapply"}, call("action_apply"), i18n("saveapply"), 10)
end
function convert_changes(changes)
local ret = {}
local util = require "luci.util"
local ret
for r, tbl in pairs(changes) do
for s, os in pairs(tbl) do
for o, v in pairs(os) do
local val, str
if (v == "") then
str = "-"
val = ""
else
str = ""
val = "="..luci.util.pcdata(v)
end
str = r.."."..s
if o ~= ".type" then
str = str.."."..o
end
table.insert(ret, str..val)
ret = (ret and ret.."\n" or "") .. "%s%s.%s%s%s" % {
v == "" and "-" or "",
r,
s,
o ~= ".type" and "."..o or "",
v ~= "" and "="..util.pcdata(v) or ""
}
end
end
end
return table.concat(ret, "\n")
return ret
end
function action_changes()
@ -53,49 +49,37 @@ function action_changes()
end
function action_apply()
local path = luci.dispatcher.context.path
local uci = luci.model.uci.cursor()
local changes = uci:changes()
local output = ""
if changes then
local com = {}
local run = {}
-- Collect files to be applied and commit changes
for r, tbl in pairs(changes) do
if r then
uci:load(r)
uci:commit(r)
uci:unload(r)
if luci.config.uci_oncommit and luci.config.uci_oncommit[r] then
run[luci.config.uci_oncommit[r]] = true
end
end
end
-- Search for post-commit commands
for cmd, i in pairs(run) do
output = output .. cmd .. ":\n" .. luci.util.exec(cmd) .. "\n"
end
local reload = {}
-- Collect files to be applied and commit changes
for r, tbl in pairs(changes) do
table.insert(reload, r)
uci:load(r)
uci:commit(r)
uci:unload(r)
end
luci.template.render("mini/uci_apply", {changes=convert_changes(changes), output=output})
local function _reload()
local cmd = uci:apply(reload, true)
return io.popen(cmd)
end
luci.template.render("mini/uci_apply", {changes=convert_changes(changes), reload=_reload})
end
function action_revert()
local uci = luci.model.uci.cursor()
local changes = uci:changes()
if changes then
local revert = {}
-- Collect files to be reverted
for r, tbl in pairs(changes) do
uci:load(r)
uci:revert(r)
uci:unload(r)
end
-- Collect files to be reverted
for r, tbl in pairs(changes) do
uci:load(r)
uci:revert(r)
uci:unload(r)
end
luci.template.render("mini/uci_revert", {changes=convert_changes(changes)})

View file

@ -16,5 +16,14 @@ $Id$
<h1><%:config%></h1>
<p><%:uci_applied%>:</p>
<code><%=(changes or "-")%>
<%=output%></code>
<%
local fp = reload()
local line = fp:read()
while line do
write(line.."\n")
line = fp:read()
end
fp:close()
%></code>
<%+footer%>

View file

@ -34,7 +34,13 @@ $Id$
</div>
</form>
<% elseif ret then %>
<% if ret == 0 then %>
<p><%:a_s_flash_received%></p>
<p><%:a_s_flash_inprogress%></p>
<!-- <%=string.rep(" ", 2048)%> -->
<% %>
<% local ret = ret()
if ret == 0 then %>
<div class="ok"><%:a_s_flash_flashed%></div>
<% else %>
<div class="error"><%:a_s_flash_flasherr%>! (<%:code%> <%=ret%>)</div>
@ -42,4 +48,5 @@ $Id$
<% else %>
<div class="error"><%:a_s_flash_notimplemented%></div>
<% end %>
<%+footer%>
<%+footer%>
<% if ret == 0 then luci.sys.reboot() end %>