+
+ uci:save("luci_splash")
+
+ -- Get current IPs and MAC addresses
+ local macs = get_known_macs()
+ local ips = get_known_ips(macs)
+
+ ipt:resync()
+
+ ipt_delete_all({table="filter", chain="luci_splash_filter", options={"MAC"}},
+ function(r) return not macs[r.options[2]:lower()] end)
+
+ ipt_delete_all({table="nat", chain="luci_splash_leases", options={"MAC"}},
+ function(r) return not macs[r.options[2]:lower()] end)
+
+ ipt_delete_all({table="mangle", chain="luci_splash_mark_out", options={"MAC", "MARK", "set"}},
+ function(r) return not macs[r.options[2]:lower()] end)
+
+ ipt_delete_all({table="mangle", chain="luci_splash_mark_in", options={"MARK", "set"}},
+ function(r) return not ips[r.destination] end)
+
+ unlock()
+end
+
+-- Show client info
+function list()
+ -- Get current arp cache
+ local arpcache = { }
+ for _, entry in ipairs(net.arptable()) do
+ arpcache[entry["HW address"]] = { entry["Device"], entry["IP address"] }
+ end
+
+ -- Find traffic usage
+ local function traffic(lease)
+ local traffic_in = 0
+ local traffic_out = 0
+
+ local rin = ipt:find({table="mangle", chain="luci_splash_mark_in", destination=lease.ipaddr})
+ local rout = ipt:find({table="mangle", chain="luci_splash_mark_out", options={"MAC", lease.mac:upper()}})
+
+ if rin and #rin > 0 then traffic_in = math.floor( rin[1].bytes / 1024) end
+ if rout and #rout > 0 then traffic_out = math.floor(rout[1].bytes / 1024) end
+
+ return traffic_in, traffic_out
+ end
+
+ -- Print listings
+ local leases = uci:get_all("luci_splash")
+
+ print(string.format(
+ "%-17s %-15s %-9s %-4s %-7s %20s",
+ "MAC", "IP", "State", "Dur.", "Intf.", "Traffic down/up"
+ ))
+
+ -- Leases
+ for _, s in pairs(leases) do
+ if s[".type"] == "lease" and s.mac then
+ local ti, to = traffic(s)
+ local mac = s.mac:lower()
+ local arp = arpcache[mac]
+ print(string.format(
+ "%-17s %-15s %-9s %3dm %-7s %7dKB %7dKB",
+ mac, s.ipaddr, "leased",
+ math.floor(( os.time() - tonumber(s.start) ) / 60),
+ arp and arp[1] or "?", ti, to
+ ))
+ end
+ end
+
+ -- Whitelist, Blacklist
+ for _, s in luci.util.spairs(leases,
+ function(a,b) return leases[a][".type"] > leases[b][".type"] end
+ ) do
+ if (s[".type"] == "whitelist" or s[".type"] == "blacklist") and s.mac then
+ local mac = s.mac:lower()
+ local arp = arpcache[mac]
+ print(string.format(
+ "%-17s %-15s %-9s %4s %-7s %9s %9s",
+ mac, arp and arp[2] or "?", s[".type"], "- ",
+ arp and arp[1] or "?", "-", "-"
+ ))