diff --git a/modules/admin-mini/luasrc/controller/mini/network.lua b/modules/admin-mini/luasrc/controller/mini/network.lua
index 8b9356d..1616681 100644
--- a/modules/admin-mini/luasrc/controller/mini/network.lua
+++ b/modules/admin-mini/luasrc/controller/mini/network.lua
@@ -20,4 +20,14 @@ function index()
 	entry({"mini", "network", "index"}, cbi("mini/network", {autoapply=true}), _("General"), 1)
 	entry({"mini", "network", "wifi"}, cbi("mini/wifi", {autoapply=true}), _("Wifi"), 10)
 	entry({"mini", "network", "dhcp"}, cbi("mini/dhcp", {autoapply=true}), _("DHCP"), 20)
+	page = entry({"mini", "network", "dhcplease_status"}, call("lease_status"), nil)
+	page.leaf = true
 end
+
+function lease_status()
+	local s = require "luci.tools.status"
+
+	luci.http.prepare_content("application/json")
+	luci.http.write_json(s.dhcp_leases())
+end
+
diff --git a/modules/admin-mini/luasrc/model/cbi/mini/dhcp.lua b/modules/admin-mini/luasrc/model/cbi/mini/dhcp.lua
index 5547db6..b06c1de 100644
--- a/modules/admin-mini/luasrc/model/cbi/mini/dhcp.lua
+++ b/modules/admin-mini/luasrc/model/cbi/mini/dhcp.lua
@@ -2,7 +2,6 @@
 LuCI - Lua Configuration Interface
 
 Copyright 2008 Steven Barth <steven@midlink.org>
-Copyright 2008 Jo-Philipp Wich <xm@leipzig.freifunk.net>
 
 Licensed under the Apache License, Version 2.0 (the "License");
 you may not use this file except in compliance with the License.
@@ -13,90 +12,234 @@ You may obtain a copy of the License at
 $Id$
 ]]--
 
-local uci = require "luci.model.uci".cursor()
 local sys = require "luci.sys"
-local wa  = require "luci.tools.webadmin"
-local fs  = require "nixio.fs"
 
-m = Map("dhcp", "DHCP")
+m = Map("dhcp", translate("DHCP and DNS"),
+	translate("Dnsmasq is a combined <abbr title=\"Dynamic Host Configuration Protocol" ..
+		"\">DHCP</abbr>-Server and <abbr title=\"Domain Name System\">DNS</abbr>-" ..
+		"Forwarder for <abbr title=\"Network Address Translation\">NAT</abbr> " ..
+		"firewalls"))
 
-s = m:section(TypedSection, "dhcp", "DHCP-Server")
+s = m:section(TypedSection, "dnsmasq", translate("Server Settings"))
 s.anonymous = true
 s.addremove = false
-s.dynamic = false
-
-s:depends("interface", "lan")
-
-enable = s:option(ListValue, "ignore", translate("enable"), "")
-enable:value(0, translate("enable"))
-enable:value(1, translate("disable"))
-
-start = s:option(Value, "start", translate("First leased address"))
-start.rmempty = true
-start:depends("ignore", "0")
-
-
-limit = s:option(Value, "limit", translate("Number of leased addresses"), "")
-limit:depends("ignore", "0")
-
-function limit.cfgvalue(self, section)
-	local value = Value.cfgvalue(self, section)
-	
-	if value then
-		return tonumber(value) + 1
-	end 
-end
-
-function limit.write(self, section, value)
-	value = tonumber(value) - 1
-	return Value.write(self, section, value) 
-end
-
-limit.rmempty = true
-
-time = s:option(Value, "leasetime")
-time:depends("ignore", "0")
-time.rmempty = true
-
-
-local leasefn, leasefp, leases
-uci:foreach("dhcp", "dnsmasq",
- function(section)
- 	leasefn = section.leasefile
- end
-) 
-local leasefp = leasefn and fs.access(leasefn) and io.lines(leasefn)
-if leasefp then
-	leases = {}
-	for lease in leasefp do
-		table.insert(leases, luci.util.split(lease, " "))
-	end
-end
-
-if leases then
-	v = m:section(Table, leases, translate("Active Leases"))
-	name = v:option(DummyValue, 4, translate("Hostname"))
-	function name.cfgvalue(self, ...)
-		local value = DummyValue.cfgvalue(self, ...)
-		return (value == "*") and "?" or value
-	end
-	ip = v:option(DummyValue, 3, translate("<abbr title=\"Internet Protocol Version 4\">IPv4</abbr>-Address"))
-	mac  = v:option(DummyValue, 2, translate("<abbr title=\"Media Access Control\">MAC</abbr>-Address"))
-	ltime = v:option(DummyValue, 1, translate("Leasetime remaining"))
-	function ltime.cfgvalue(self, ...)
-		local value = DummyValue.cfgvalue(self, ...)
-		return wa.date_format(os.difftime(tonumber(value), os.time()))
-	end
-end
-
-s2 = m:section(TypedSection, "host", translate("Static Leases"))
-s2.addremove = true
-s2.anonymous = true
-s2.template = "cbi/tblsection"
-
-name = s2:option(Value, "name", translate("Hostname"))
-mac = s2:option(Value, "mac", translate("<abbr title=\"Media Access Control\">MAC</abbr>-Address"))
-ip = s2:option(Value, "ip", translate("<abbr title=\"Internet Protocol Version 4\">IPv4</abbr>-Address"))
+
+s:tab("general", translate("General Settings"))
+s:tab("files", translate("Resolv and Hosts Files"))
+s:tab("tftp", translate("TFTP Settings"))
+s:tab("advanced", translate("Advanced Settings"))
+
+s:taboption("general", Flag, "domainneeded",
+	translate("Domain required"),
+	translate("Don't forward <abbr title=\"Domain Name System\">DNS</abbr>-Requests without " ..
+		"<abbr title=\"Domain Name System\">DNS</abbr>-Name"))
+
+s:taboption("general", Flag, "authoritative",
+	translate("Authoritative"),
+	translate("This is the only <abbr title=\"Dynamic Host Configuration Protocol\">DHCP</" ..
+		"abbr> in the local network"))
+
+
+s:taboption("files", Flag, "readethers",
+	translate("Use <code>/etc/ethers</code>"),
+	translate("Read <code>/etc/ethers</code> to configure the <abbr title=\"Dynamic Host " ..
+		"Configuration Protocol\">DHCP</abbr>-Server"))
+
+s:taboption("files", Value, "leasefile",
+	translate("Leasefile"),
+	translate("file where given <abbr title=\"Dynamic Host Configuration Protocol\">DHCP</" ..
+		"abbr>-leases will be stored"))
+
+s:taboption("files", Flag, "noresolv",
+	translate("Ignore resolve file")).optional = true
+
+rf = s:taboption("files", Value, "resolvfile",
+	translate("Resolve file"),
+	translate("local <abbr title=\"Domain Name System\">DNS</abbr> file"))
+
+rf:depends("noresolv", "")
+rf.optional = true
+
+
+s:taboption("files", Flag, "nohosts",
+	translate("Ignore Hosts files")).optional = true
+
+hf = s:taboption("files", DynamicList, "addnhosts",
+	translate("Additional Hosts files"))
+
+hf:depends("nohosts", "")
+hf.optional = true
+
+
+s:taboption("advanced", Flag, "boguspriv",
+	translate("Filter private"),
+	translate("Do not forward reverse lookups for local networks"))
+
+s:taboption("advanced", Flag, "filterwin2k",
+	translate("Filter useless"),
+	translate("Do not forward requests that cannot be answered by public name servers"))
+
+
+s:taboption("advanced", Flag, "localise_queries",
+	translate("Localise queries"),
+	translate("Localise hostname depending on the requesting subnet if multiple IPs are available"))
+
+s:taboption("general", Value, "local",
+	translate("Local server"),
+	translate("Local domain specification. Names matching this domain are never forwared and resolved from DHCP or hosts files only"))
+
+s:taboption("general", Value, "domain",
+	translate("Local domain"),
+	translate("Local domain suffix appended to DHCP names and hosts file entries"))
+
+s:taboption("advanced", Flag, "expandhosts",
+	translate("Expand hosts"),
+	translate("Add local domain suffix to names served from hosts files"))
+
+s:taboption("advanced", Flag, "nonegcache",
+	translate("No negative cache"),
+	translate("Do not cache negative replies, e.g. for not existing domains"))
+
+s:taboption("advanced", Flag, "strictorder",
+	translate("Strict order"),
+	translate("<abbr title=\"Domain Name System\">DNS</abbr> servers will be queried in the " ..
+		"order of the resolvfile")).optional = true
+
+
+bn = s:taboption("advanced", DynamicList, "bogusnxdomain", translate("Bogus NX Domain Override"),
+	translate("List of hosts that supply bogus NX domain results"))
+
+bn.optional = true
+bn.placeholder = "67.215.65.132"
+
+
+s:taboption("general", Flag, "logqueries",
+	translate("Log queries"),
+	translate("Write received DNS requests to syslog")).optional = true
+
+df = s:taboption("general", DynamicList, "server", translate("DNS forwardings"),
+	translate("List of <abbr title=\"Domain Name System\">DNS</abbr> " ..
+			"servers to forward requests to"))
+
+df.optional = true
+df.placeholder = "/example.org/10.1.2.3"
+
+
+rp = s:taboption("general", Flag, "rebind_protection",
+	translate("Rebind protection"),
+	translate("Discard upstream RFC1918 responses"))
+
+rp.rmempty = false
+
+
+rl = s:taboption("general", Flag, "rebind_localhost",
+	translate("Allow localhost"),
+	translate("Allow upstream responses in the 127.0.0.0/8 range, e.g. for RBL services"))
+
+rl:depends("rebind_protection", "1")
+
+
+rd = s:taboption("general", DynamicList, "rebind_domain",
+	translate("Domain whitelist"),
+	translate("List of domains to allow RFC1918 responses for"))
+
+rd:depends("rebind_protection", "1")
+rd.datatype = "host"
+rd.placeholder = "ihost.netflix.com"
+
+
+pt = s:taboption("advanced", Value, "port",
+	translate("<abbr title=\"Domain Name System\">DNS</abbr> server port"),
+	translate("Listening port for inbound DNS queries"))
+
+pt.optional = true
+pt.datatype = "port"
+pt.placeholder = 53
+
+
+qp = s:taboption("advanced", Value, "queryport",
+	translate("<abbr title=\"Domain Name System\">DNS</abbr> query port"),
+	translate("Fixed source port for outbound DNS queries"))
+
+qp.optional = true
+qp.datatype = "port"
+qp.placeholder = translate("any")
+
+
+lm = s:taboption("advanced", Value, "dhcpleasemax",
+	translate("<abbr title=\"maximal\">Max.</abbr> <abbr title=\"Dynamic Host Configuration " ..
+		"Protocol\">DHCP</abbr> leases"),
+	translate("Maximum allowed number of active DHCP leases"))
+
+lm.optional = true
+lm.datatype = "uinteger"
+lm.placeholder = translate("unlimited")
+
+
+em = s:taboption("advanced", Value, "ednspacket_max",
+	translate("<abbr title=\"maximal\">Max.</abbr> <abbr title=\"Extension Mechanisms for " ..
+		"Domain Name System\">EDNS0</abbr> paket size"),
+	translate("Maximum allowed size of EDNS.0 UDP packets"))
+
+em.optional = true
+em.datatype = "uinteger"
+em.placeholder = 1280
+
+
+cq = s:taboption("advanced", Value, "dnsforwardmax",
+	translate("<abbr title=\"maximal\">Max.</abbr> concurrent queries"),
+	translate("Maximum allowed number of concurrent DNS queries"))
+
+cq.optional = true
+cq.datatype = "uinteger"
+cq.placeholder = 150
+
+
+s:taboption("tftp", Flag, "enable_tftp",
+	translate("Enable TFTP server")).optional = true
+
+tr = s:taboption("tftp", Value, "tftp_root",
+	translate("TFTP server root"),
+	translate("Root directory for files served via TFTP"))
+
+tr.optional = true
+tr:depends("enable_tftp", "1")
+tr.placeholder = "/"
+
+
+db = s:taboption("tftp", Value, "dhcp_boot",
+	translate("Network boot image"),
+	translate("Filename of the boot image advertised to clients"))
+
+db.optional = true
+db:depends("enable_tftp", "1")
+db.placeholder = "pxelinux.0"
+
+
+m:section(SimpleSection).template = "mini/lease_status"
+
+s = m:section(TypedSection, "host", translate("Static Leases"),
+	translate("Static leases are used to assign fixed IP addresses and symbolic hostnames to " ..
+		"DHCP clients. They are also required for non-dynamic interface configurations where " ..
+		"only hosts with a corresponding lease are served.") .. "<br />" ..
+	translate("Use the <em>Add</em> Button to add a new lease entry. The <em>MAC-Address</em> " ..
+		"indentifies the host, the <em>IPv4-Address</em> specifies to the fixed address to " ..
+		"use and the <em>Hostname</em> is assigned as symbolic name to the requesting host."))
+
+s.addremove = true
+s.anonymous = true
+s.template = "cbi/tblsection"
+
+name = s:option(Value, "name", translate("Hostname"))
+name.datatype = "hostname"
+name.rmempty  = true
+
+mac = s:option(Value, "mac", translate("<abbr title=\"Media Access Control\">MAC</abbr>-Address"))
+mac.datatype = "list(macaddr)"
+
+ip = s:option(Value, "ip", translate("<abbr title=\"Internet Protocol Version 4\">IPv4</abbr>-Address"))
+ip.datatype = "ip4addr"
+
 sys.net.arptable(function(entry)
 	ip:value(entry["IP address"])
 	mac:value(
@@ -105,5 +248,5 @@ sys.net.arptable(function(entry)
 	)
 end)
 
-return m
 
+return m
--- a/modules/admin-mini/luasrc/view/mini/lease_status.htm	2012-06-07 20:34:02.149931178 +0200
+++ b/modules/admin-mini/luasrc/view/mini/lease_status.htm	2012-06-26 09:55:54.960961486 +0200
@@ -0,0 +1,61 @@
+<script type="text/javascript">//<![CDATA[
+	XHR.poll(5, '<%=luci.dispatcher.build_url("mini", "network", "dhcplease_status")%>', null,
+		function(x, st)
+		{
+			var tb = document.getElementById('lease_status_table');
+			if (st && tb)
+			{
+				/* clear all rows */
+				while( tb.rows.length > 1 )
+					tb.deleteRow(1);
+
+				for( var i = 0; i < st.length; i++ )
+				{
+					var timestr;
+
+					if (st[i].expires <= 0)
+					{
+						timestr = '<em><%:expired%></em>';
+					}
+					else
+					{
+						timestr = String.format('%t', st[i].expires);
+					}
+
+					var tr = tb.insertRow(-1);
+						tr.className = 'cbi-section-table-row cbi-rowstyle-' + ((i % 2) + 1);
+
+					tr.insertCell(-1).innerHTML = st[i].hostname ? st[i].hostname : '?';
+					tr.insertCell(-1).innerHTML = st[i].ipaddr;
+					tr.insertCell(-1).innerHTML = st[i].macaddr;
+					tr.insertCell(-1).innerHTML = timestr;
+				}
+
+				if( tb.rows.length == 1 )
+				{
+					var tr = tb.insertRow(-1);
+						tr.className = 'cbi-section-table-row';
+
+					var td = tr.insertCell(-1);
+						td.colSpan = 4;
+						td.innerHTML = '<em><br /><%:There are no active leases.%></em>';
+				}
+			}
+		}
+	);
+//]]></script>
+
+<fieldset class="cbi-section">
+	<legend><%:Active Leases%></legend>
+	<table class="cbi-section-table" id="lease_status_table">
+		<tr class="cbi-section-table-titles">
+			<th class="cbi-section-table-cell"><%:Hostname%></th>
+			<th class="cbi-section-table-cell"><%:IPv4-Address%></th>
+			<th class="cbi-section-table-cell"><%:MAC-Address%></th>
+			<th class="cbi-section-table-cell"><%:Leasetime remaining%></th>
+		</tr>
+		<tr class="cbi-section-table-row">
+			<td colspan="4"><em><br /><%:Collecting data...%></em></td>
+		</tr>
+	</table>
+</fieldset>
