Project

General

Profile

Download (34.6 KB) Statistics
| Branch: | Tag: | Revision:
1
<?php
2
/*
3
	services_dhcpv6.php
4
*/
5
/* ====================================================================
6
 *	Copyright (c)  2004-2015  Electric Sheep Fencing, LLC. All rights reserved.
7
 *	Copyright (c)  2010 Seth Mos <seth.mos@dds.nl>
8
 *
9
 *	Some or all of this file is based on the m0n0wall project which is
10
 *	Copyright (c)  2004 Manuel Kasper (BSD 2 clause)
11
 *
12
 *	Redistribution and use in source and binary forms, with or without modification,
13
 *	are permitted provided that the following conditions are met:
14
 *
15
 *	1. Redistributions of source code must retain the above copyright notice,
16
 *		this list of conditions and the following disclaimer.
17
 *
18
 *	2. Redistributions in binary form must reproduce the above copyright
19
 *		notice, this list of conditions and the following disclaimer in
20
 *		the documentation and/or other materials provided with the
21
 *		distribution.
22
 *
23
 *	3. All advertising materials mentioning features or use of this software
24
 *		must display the following acknowledgment:
25
 *		"This product includes software developed by the pfSense Project
26
 *		 for use in the pfSense software distribution. (http://www.pfsense.org/).
27
 *
28
 *	4. The names "pfSense" and "pfSense Project" must not be used to
29
 *		 endorse or promote products derived from this software without
30
 *		 prior written permission. For written permission, please contact
31
 *		 coreteam@pfsense.org.
32
 *
33
 *	5. Products derived from this software may not be called "pfSense"
34
 *		nor may "pfSense" appear in their names without prior written
35
 *		permission of the Electric Sheep Fencing, LLC.
36
 *
37
 *	6. Redistributions of any form whatsoever must retain the following
38
 *		acknowledgment:
39
 *
40
 *	"This product includes software developed by the pfSense Project
41
 *	for use in the pfSense software distribution (http://www.pfsense.org/).
42
 *
43
 *	THIS SOFTWARE IS PROVIDED BY THE pfSense PROJECT ``AS IS'' AND ANY
44
 *	EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
45
 *	IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
46
 *	PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE pfSense PROJECT OR
47
 *	ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
48
 *	SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
49
 *	NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
50
 *	LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
51
 *	HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
52
 *	STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
53
 *	ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
54
 *	OF THE POSSIBILITY OF SUCH DAMAGE.
55
 *
56
 *	====================================================================
57
 *
58
 */
59

    
60
##|+PRIV
61
##|*IDENT=page-services-dhcpv6server
62
##|*NAME=Services: DHCPv6 server
63
##|*DESCR=Allow access to the 'Services: DHCPv6 server' page.
64
##|*MATCH=services_dhcpv6.php*
65
##|-PRIV
66

    
67
require("guiconfig.inc");
68
require_once("filter.inc");
69

    
70
function dhcpv6_apply_changes($dhcpdv6_enable_changed) {
71
	$retval = 0;
72
	$retvaldhcp = 0;
73
	$retvaldns = 0;
74
	/* Stop DHCPv6 so we can cleanup leases */
75
	killbypid("{$g['dhcpd_chroot_path']}{$g['varrun_path']}/dhcpdv6.pid");
76
	// dhcp_clean_leases();
77
	/* dnsmasq_configure calls dhcpd_configure */
78
	/* no need to restart dhcpd twice */
79
	if (isset($config['dnsmasq']['enable']) && isset($config['dnsmasq']['regdhcpstatic']))	{
80
		$retvaldns = services_dnsmasq_configure();
81
		if ($retvaldns == 0) {
82
			clear_subsystem_dirty('hosts');
83
			clear_subsystem_dirty('staticmaps');
84
		}
85
	} else if (isset($config['unbound']['enable']) && isset($config['unbound']['regdhcpstatic'])) {
86
		$retvaldns = services_unbound_configure();
87
		if ($retvaldns == 0) {
88
			clear_subsystem_dirty('unbound');
89
			clear_subsystem_dirty('staticmaps');
90
		}
91
	} else {
92
		$retvaldhcp = services_dhcpd_configure();
93
		if ($retvaldhcp == 0) {
94
			clear_subsystem_dirty('staticmaps');
95
		}
96
	}
97
	if ($dhcpdv6_enable_changed) {
98
		$retvalfc = filter_configure();
99
	}
100
	if ($retvaldhcp == 1 || $retvaldns == 1 || $retvalfc == 1) {
101
		$retval = 1;
102
	}
103
	return get_std_save_message($retval);
104
}
105

    
106
if (!$g['services_dhcp_server_enable']) {
107
	header("Location: /");
108
	exit;
109
}
110

    
111
/*	Fix failover DHCP problem
112
 *	http://article.gmane.org/gmane.comp.security.firewalls.pfsense.support/18749
113
 */
114
ini_set("memory_limit", "64M");
115

    
116
$if = $_GET['if'];
117
if ($_POST['if']) {
118
	$if = $_POST['if'];
119
}
120

    
121
/* if OLSRD is enabled, allow WAN to house DHCP. */
122
if ($config['installedpackages']['olsrd']) {
123
	foreach ($config['installedpackages']['olsrd']['config'] as $olsrd) {
124
		if ($olsrd['enable']) {
125
			$is_olsr_enabled = true;
126
			break;
127
		}
128
	}
129
}
130

    
131
$iflist = get_configured_interface_with_descr();
132
$iflist = array_merge($iflist, get_configured_pppoe_server_interfaces());
133

    
134
/* set the starting interface */
135
if (!$if || !isset($iflist[$if])) {
136
	foreach ($iflist as $ifent => $ifname) {
137
		$oc = $config['interfaces'][$ifent];
138
		$valid_if_ipaddrv6 = (bool) ($oc['ipaddrv6'] == 'track6' ||
139
		    (is_ipaddrv6($oc['ipaddrv6']) &&
140
		    !is_linklocal($oc['ipaddrv6'])));
141

    
142
		if ((!is_array($config['dhcpdv6'][$ifent]) ||
143
		    !isset($config['dhcpdv6'][$ifent]['enable'])) &&
144
		    !$valid_if_ipaddrv6) {
145
			continue;
146
		}
147
		$if = $ifent;
148
		break;
149
	}
150
}
151

    
152
if (is_array($config['dhcpdv6'][$if])) {
153
	/* DHCPv6 */
154
	if (is_array($config['dhcpdv6'][$if]['range'])) {
155
		$pconfig['range_from'] = $config['dhcpdv6'][$if]['range']['from'];
156
		$pconfig['range_to'] = $config['dhcpdv6'][$if]['range']['to'];
157
	}
158
	if (is_array($config['dhcpdv6'][$if]['prefixrange'])) {
159
		$pconfig['prefixrange_from'] = $config['dhcpdv6'][$if]['prefixrange']['from'];
160
		$pconfig['prefixrange_to'] = $config['dhcpdv6'][$if]['prefixrange']['to'];
161
		$pconfig['prefixrange_length'] = $config['dhcpdv6'][$if]['prefixrange']['prefixlength'];
162
	}
163
	$pconfig['deftime'] = $config['dhcpdv6'][$if]['defaultleasetime'];
164
	$pconfig['maxtime'] = $config['dhcpdv6'][$if]['maxleasetime'];
165
	$pconfig['domain'] = $config['dhcpdv6'][$if]['domain'];
166
	$pconfig['domainsearchlist'] = $config['dhcpdv6'][$if]['domainsearchlist'];
167
	list($pconfig['wins1'], $pconfig['wins2']) = $config['dhcpdv6'][$if]['winsserver'];
168
	list($pconfig['dns1'], $pconfig['dns2'], $pconfig['dns3'], $pconfig['dns4']) = $config['dhcpdv6'][$if]['dnsserver'];
169
	$pconfig['enable'] = isset($config['dhcpdv6'][$if]['enable']);
170
	$pconfig['ddnsdomain'] = $config['dhcpdv6'][$if]['ddnsdomain'];
171
	$pconfig['ddnsdomainprimary'] = $config['dhcpdv6'][$if]['ddnsdomainprimary'];
172
	$pconfig['ddnsdomainkeyname'] = $config['dhcpdv6'][$if]['ddnsdomainkeyname'];
173
	$pconfig['ddnsdomainkey'] = $config['dhcpdv6'][$if]['ddnsdomainkey'];
174
	$pconfig['ddnsupdate'] = isset($config['dhcpdv6'][$if]['ddnsupdate']);
175
	$pconfig['ddnsreverse'] = isset($config['dhcpdv6'][$if]['ddnsreverse']);
176
	$pconfig['ddnsclientupdates'] = $config['dhcpdv6'][$if]['ddnsclientupdates'];
177
	list($pconfig['ntp1'], $pconfig['ntp2']) = $config['dhcpdv6'][$if]['ntpserver'];
178
	$pconfig['tftp'] = $config['dhcpdv6'][$if]['tftp'];
179
	$pconfig['ldap'] = $config['dhcpdv6'][$if]['ldap'];
180
	$pconfig['netboot'] = isset($config['dhcpdv6'][$if]['netboot']);
181
	$pconfig['bootfile_url'] = $config['dhcpdv6'][$if]['bootfile_url'];
182
	$pconfig['netmask'] = $config['dhcpdv6'][$if]['netmask'];
183
	$pconfig['numberoptions'] = $config['dhcpdv6'][$if]['numberoptions'];
184
	$pconfig['dhcpv6leaseinlocaltime'] = $config['dhcpdv6'][$if]['dhcpv6leaseinlocaltime'];
185
	if (!is_array($config['dhcpdv6'][$if]['staticmap'])) {
186
		$config['dhcpdv6'][$if]['staticmap'] = array();
187
	}
188
	$a_maps = &$config['dhcpdv6'][$if]['staticmap'];
189
}
190

    
191
if ($config['interfaces'][$if]['ipaddrv6'] == 'track6') {
192
	$trackifname = $config['interfaces'][$if]['track6-interface'];
193
	$trackcfg = $config['interfaces'][$trackifname];
194
	$ifcfgsn = "64";
195
	$ifcfgip = '::';
196

    
197
	$str_help_mask = dhcpv6_pd_str_help($ifcfgsn);
198
} else {
199
	$ifcfgip = get_interface_ipv6($if);
200
	$ifcfgsn = get_interface_subnetv6($if);
201
}
202

    
203
/*	 set the enabled flag which will tell us if DHCP relay is enabled
204
 *	 on any interface. We will use this to disable DHCP server since
205
 *	 the two are not compatible with each other.
206
 */
207

    
208
$dhcrelay_enabled = false;
209
$dhcrelaycfg = $config['dhcrelay6'];
210

    
211
if (is_array($dhcrelaycfg) && isset($dhcrelaycfg['enable']) && isset($dhcrelaycfg['interface']) && !empty($dhcrelaycfg['interface'])) {
212
	$dhcrelayifs = explode(",", $dhcrelaycfg['interface']);
213

    
214
	foreach ($dhcrelayifs as $dhcrelayif) {
215

    
216
		if (isset($iflist[$dhcrelayif]) && (!link_interface_to_bridge($dhcrelayif))) {
217
			$dhcrelay_enabled = true;
218
			break;
219
		}
220
	}
221
}
222

    
223
if ($_POST['apply'] == "Apply Changes") {
224
	$savemsg = dhcpv6_apply_changes(false);
225
} elseif ($_POST['Submit'] == "Save") {
226
	unset($input_errors);
227

    
228
	$old_dhcpdv6_enable = ($pconfig['enable'] == true);
229
	$new_dhcpdv6_enable = ($_POST['enable'] ? true : false);
230
	$dhcpdv6_enable_changed = ($old_dhcpdv6_enable != $new_dhcpdv6_enable);
231

    
232
	$pconfig = $_POST;
233

    
234
	$numberoptions = array();
235
	for ($x = 0; $x < 99; $x++) {
236
		if (isset($_POST["number{$x}"]) && ctype_digit($_POST["number{$x}"])) {
237
			$numbervalue = array();
238
			$numbervalue['number'] = htmlspecialchars($_POST["number{$x}"]);
239
			$numbervalue['value'] = base64_encode($_POST["value{$x}"]);
240
			$numberoptions['item'][] = $numbervalue;
241
		}
242
	}
243
	// Reload the new pconfig variable that the forum uses.
244
	$pconfig['numberoptions'] = $numberoptions;
245

    
246
	/* input validation */
247
	if ($_POST['enable']) {
248
		$reqdfields = explode(" ", "range_from range_to");
249
		$reqdfieldsn = array(gettext("Range begin"), gettext("Range end"));
250

    
251
		do_input_validation($_POST, $reqdfields, $reqdfieldsn, $input_errors);
252

    
253
		if (($_POST['prefixrange_from'] && !is_ipaddrv6($_POST['prefixrange_from']))) {
254
			$input_errors[] = gettext("A valid prefix range must be specified.");
255
		}
256
		if (($_POST['prefixrange_to'] && !is_ipaddrv6($_POST['prefixrange_to']))) {
257
			$input_errors[] = gettext("A valid prefix range must be specified.");
258
		}
259

    
260
		if ($_POST['prefixrange_from'] && $_POST['prefixrange_to'] &&
261
		    $_POST['prefixrange_length']) {
262
			$netmask = Net_IPv6::getNetmask($_POST['prefixrange_from'],
263
			    $_POST['prefixrange_length']);
264
			$netmask = Net_IPv6::compress($netmask);
265

    
266
			if ($netmask != Net_IPv6::compress(strtolower(
267
			    $_POST['prefixrange_from']))) {
268
				$input_errors[] = sprintf(gettext(
269
				    "Prefix Delegation From address is not a valid IPv6 Netmask for %s"),
270
				    $netmask . '/' . $_POST['prefixrange_length']);
271
			}
272

    
273
			$netmask = Net_IPv6::getNetmask($_POST['prefixrange_to'],
274
			    $_POST['prefixrange_length']);
275
			$netmask = Net_IPv6::compress($netmask);
276

    
277
			if ($netmask != Net_IPv6::compress(strtolower(
278
			    $_POST['prefixrange_to']))) {
279
				$input_errors[] = sprintf(gettext(
280
				    "Prefix Delegation To address is not a valid IPv6 Netmask for %s"),
281
				    $netmask . '/' . $_POST['prefixrange_length']);
282
			}
283
		}
284

    
285
		if ($_POST['range_from']) {
286
			if (!is_ipaddrv6($_POST['range_from'])) {
287
				$input_errors[] = gettext("A valid range must be specified.");
288
			} elseif ($config['interfaces'][$if]['ipaddrv6'] == 'track6' &&
289
			    !Net_IPv6::isInNetmask($_POST['range_from'], '::', $ifcfgsn)) {
290
				$input_errors[] = sprintf(gettext(
291
				    "The prefix (upper %s bits) must be zero.  Use the form %s"),
292
				    $ifcfgsn, $str_help_mask);
293
			}
294
		}
295
		if ($_POST['range_to']) {
296
			if (!is_ipaddrv6($_POST['range_to'])) {
297
				$input_errors[] = gettext("A valid range must be specified.");
298
			} elseif ($config['interfaces'][$if]['ipaddrv6'] == 'track6' &&
299
			    !Net_IPv6::isInNetmask($_POST['range_to'], '::', $ifcfgsn)) {
300
				$input_errors[] = sprintf(gettext(
301
				    "The prefix (upper %s bits) must be zero.  Use the form %s"),
302
				    $ifcfgsn, $str_help_mask);
303
			}
304
		}
305
		if (($_POST['gateway'] && !is_ipaddrv6($_POST['gateway']))) {
306
			$input_errors[] = gettext("A valid IPv6 address must be specified for the gateway.");
307
		}
308
		if (($_POST['dns1'] && !is_ipaddrv6($_POST['dns1'])) ||
309
		    ($_POST['dns2'] && !is_ipaddrv6($_POST['dns2'])) ||
310
		    ($_POST['dns3'] && !is_ipaddrv6($_POST['dns3'])) ||
311
		    ($_POST['dns4'] && !is_ipaddrv6($_POST['dns4']))) {
312
			$input_errors[] = gettext("A valid IPv6 address must be specified for each of the DNS servers.");
313
		}
314

    
315
		if ($_POST['deftime'] && (!is_numeric($_POST['deftime']) || ($_POST['deftime'] < 60))) {
316
			$input_errors[] = gettext("The default lease time must be at least 60 seconds.");
317
		}
318
		if ($_POST['maxtime'] && (!is_numeric($_POST['maxtime']) || ($_POST['maxtime'] < 60) || ($_POST['maxtime'] <= $_POST['deftime']))) {
319
			$input_errors[] = gettext("The maximum lease time must be at least 60 seconds and higher than the default lease time.");
320
		}
321
		if (($_POST['ddnsdomain'] && !is_domain($_POST['ddnsdomain']))) {
322
			$input_errors[] = gettext("A valid domain name must be specified for the dynamic DNS registration.");
323
		}
324
		if (($_POST['ddnsdomain'] && !is_ipaddrv4($_POST['ddnsdomainprimary']))) {
325
			$input_errors[] = gettext("A valid primary domain name server IPv4 address must be specified for the dynamic domain name.");
326
		}
327
		if (($_POST['ddnsdomainkey'] && !$_POST['ddnsdomainkeyname']) ||
328
		    ($_POST['ddnsdomainkeyname'] && !$_POST['ddnsdomainkey'])) {
329
			$input_errors[] = gettext("You must specify both a valid domain key and key name.");
330
		}
331
		if ($_POST['domainsearchlist']) {
332
			$domain_array=preg_split("/[ ;]+/", $_POST['domainsearchlist']);
333
			foreach ($domain_array as $curdomain) {
334
				if (!is_domain($curdomain)) {
335
					$input_errors[] = gettext("A valid domain search list must be specified.");
336
					break;
337
				}
338
			}
339
		}
340

    
341
		if (($_POST['ntp1'] && !is_ipaddrv6($_POST['ntp1'])) || ($_POST['ntp2'] && !is_ipaddrv6($_POST['ntp2']))) {
342
			$input_errors[] = gettext("A valid IPv6 address must be specified for the primary/secondary NTP servers.");
343
		}
344
		if (($_POST['domain'] && !is_domain($_POST['domain']))) {
345
			$input_errors[] = gettext("A valid domain name must be specified for the DNS domain.");
346
		}
347
		if ($_POST['tftp'] && !is_ipaddr($_POST['tftp']) && !is_domain($_POST['tftp']) && !is_URL($_POST['tftp'])) {
348
			$input_errors[] = gettext("A valid IPv6 address or hostname must be specified for the TFTP server.");
349
		}
350
		if (($_POST['bootfile_url'] && !is_URL($_POST['bootfile_url']))) {
351
			$input_errors[] = gettext("A valid URL must be specified for the network bootfile.");
352
		}
353

    
354
		// Disallow a range that includes the virtualip
355
		if (is_array($config['virtualip']['vip'])) {
356
			foreach ($config['virtualip']['vip'] as $vip) {
357
				if ($vip['interface'] == $if) {
358
					if ($vip['subnetv6'] && is_inrange_v6($vip['subnetv6'], $_POST['range_from'], $_POST['range_to'])) {
359
						$input_errors[] = sprintf(gettext("The subnet range cannot overlap with virtual IPv6 address %s."), $vip['subnetv6']);
360
					}
361
				}
362
			}
363
		}
364

    
365
		$noip = false;
366
		if (is_array($a_maps)) {
367
			foreach ($a_maps as $map) {
368
				if (empty($map['ipaddrv6'])) {
369
					$noip = true;
370
				}
371
			}
372
		}
373
		if (!$input_errors) {
374
			/* make sure the range lies within the current subnet */
375
			$subnet_start = gen_subnetv6($ifcfgip, $ifcfgsn);
376
			$subnet_end = gen_subnetv6_max($ifcfgip, $ifcfgsn);
377

    
378
			if (is_ipaddrv6($ifcfgip)) {
379
				if ((!is_inrange_v6($_POST['range_from'], $subnet_start, $subnet_end)) ||
380
				    (!is_inrange_v6($_POST['range_to'], $subnet_start, $subnet_end))) {
381
					$input_errors[] = gettext("The specified range lies outside of the current subnet.");
382
				}
383
			}
384
			/* "from" cannot be higher than "to" */
385
			if (inet_pton($_POST['range_from']) > inet_pton($_POST['range_to'])) {
386
				$input_errors[] = gettext("The range is invalid (first element higher than second element).");
387
			}
388

    
389
			/* make sure that the DHCP Relay isn't enabled on this interface */
390
			if (isset($config['dhcrelay'][$if]['enable'])) {
391
				$input_errors[] = sprintf(gettext("You must disable the DHCP relay on the %s interface before enabling the DHCP server."), $iflist[$if]);
392
			}
393

    
394

    
395
			/* Verify static mappings do not overlap:
396
			   - available DHCP range
397
			   - prefix delegation range (FIXME: still need to be completed) */
398
			$dynsubnet_start = inet_pton($_POST['range_from']);
399
			$dynsubnet_end = inet_pton($_POST['range_to']);
400

    
401
			if (is_array($a_maps)) {
402
				foreach ($a_maps as $map) {
403
					if (empty($map['ipaddrv6'])) {
404
						continue;
405
					}
406
					if ((inet_pton($map['ipaddrv6']) > $dynsubnet_start) &&
407
					    (inet_pton($map['ipaddrv6']) < $dynsubnet_end)) {
408
						$input_errors[] = sprintf(gettext("The DHCP range cannot overlap any static DHCP mappings."));
409
						break;
410
					}
411
				}
412
			}
413
		}
414
	}
415

    
416
	if (!$input_errors) {
417
		if (!is_array($config['dhcpdv6'][$if])) {
418
			$config['dhcpdv6'][$if] = array();
419
		}
420
		if (!is_array($config['dhcpdv6'][$if]['range'])) {
421
			$config['dhcpdv6'][$if]['range'] = array();
422
		}
423
		if (!is_array($config['dhcpdv6'][$if]['prefixrange'])) {
424
			$config['dhcpdv6'][$if]['prefixrange'] = array();
425
		}
426

    
427
		$config['dhcpdv6'][$if]['range']['from'] = $_POST['range_from'];
428
		$config['dhcpdv6'][$if]['range']['to'] = $_POST['range_to'];
429
		$config['dhcpdv6'][$if]['prefixrange']['from'] = $_POST['prefixrange_from'];
430
		$config['dhcpdv6'][$if]['prefixrange']['to'] = $_POST['prefixrange_to'];
431
		$config['dhcpdv6'][$if]['prefixrange']['prefixlength'] = $_POST['prefixrange_length'];
432
		$config['dhcpdv6'][$if]['defaultleasetime'] = $_POST['deftime'];
433
		$config['dhcpdv6'][$if]['maxleasetime'] = $_POST['maxtime'];
434
		$config['dhcpdv6'][$if]['netmask'] = $_POST['netmask'];
435

    
436
		unset($config['dhcpdv6'][$if]['winsserver']);
437

    
438
		unset($config['dhcpdv6'][$if]['dnsserver']);
439
		if ($_POST['dns1']) {
440
			$config['dhcpdv6'][$if]['dnsserver'][] = $_POST['dns1'];
441
		}
442
		if ($_POST['dns2']) {
443
			$config['dhcpdv6'][$if]['dnsserver'][] = $_POST['dns2'];
444
		}
445
		if ($_POST['dns3']) {
446
			$config['dhcpdv6'][$if]['dnsserver'][] = $_POST['dns3'];
447
		}
448
		if ($_POST['dns4']) {
449
			$config['dhcpdv6'][$if]['dnsserver'][] = $_POST['dns4'];
450
		}
451

    
452
		$config['dhcpdv6'][$if]['domain'] = $_POST['domain'];
453
		$config['dhcpdv6'][$if]['domainsearchlist'] = $_POST['domainsearchlist'];
454
		$config['dhcpdv6'][$if]['enable'] = ($_POST['enable']) ? true : false;
455
		$config['dhcpdv6'][$if]['ddnsdomain'] = $_POST['ddnsdomain'];
456
		$config['dhcpdv6'][$if]['ddnsdomainprimary'] = $_POST['ddnsdomainprimary'];
457
		$config['dhcpdv6'][$if]['ddnsdomainkeyname'] = $_POST['ddnsdomainkeyname'];
458
		$config['dhcpdv6'][$if]['ddnsdomainkey'] = $_POST['ddnsdomainkey'];
459
		$config['dhcpdv6'][$if]['ddnsupdate'] = ($_POST['ddnsupdate']) ? true : false;
460
		$config['dhcpdv6'][$if]['ddnsreverse'] = ($_POST['ddnsreverse']) ? true : false;
461
		$config['dhcpdv6'][$if]['ddnsclientupdates'] = $_POST['ddnsclientupdates'];
462

    
463
		unset($config['dhcpdv6'][$if]['ntpserver']);
464
		if ($_POST['ntp1']) {
465
			$config['dhcpdv6'][$if]['ntpserver'][] = $_POST['ntp1'];
466
		}
467
		if ($_POST['ntp2']) {
468
			$config['dhcpdv6'][$if]['ntpserver'][] = $_POST['ntp2'];
469
		}
470

    
471
		$config['dhcpdv6'][$if]['tftp'] = $_POST['tftp'];
472
		$config['dhcpdv6'][$if]['ldap'] = $_POST['ldap'];
473
		$config['dhcpdv6'][$if]['netboot'] = ($_POST['netboot']) ? true : false;
474
		$config['dhcpdv6'][$if]['bootfile_url'] = $_POST['bootfile_url'];
475
		$config['dhcpdv6'][$if]['dhcpv6leaseinlocaltime'] = $_POST['dhcpv6leaseinlocaltime'];
476

    
477
		// Handle the custom options rowhelper
478
		if (isset($config['dhcpdv6'][$if]['numberoptions']['item'])) {
479
			unset($config['dhcpdv6'][$if]['numberoptions']['item']);
480
		}
481

    
482
		$config['dhcpdv6'][$if]['numberoptions'] = $numberoptions;
483

    
484
		write_config();
485

    
486
		$savemsg = dhcpv6_apply_changes($dhcpdv6_enable_changed);
487
	}
488
}
489

    
490
if ($_GET['act'] == "del") {
491
	if ($a_maps[$_GET['id']]) {
492
		unset($a_maps[$_GET['id']]);
493
		write_config();
494
		if (isset($config['dhcpdv6'][$if]['enable'])) {
495
			mark_subsystem_dirty('staticmapsv6');
496
			if (isset($config['dnsmasq']['enable']) && isset($config['dnsmasq']['regdhcpstaticv6'])) {
497
				mark_subsystem_dirty('hosts');
498
			}
499
		}
500
		header("Location: services_dhcpv6.php?if={$if}");
501
		exit;
502
	}
503
}
504

    
505
$pgtitle = array(gettext("Services"), htmlspecialchars(gettext("DHCPv6 Server & RA")));
506

    
507
if (!empty($if) && !$dhcrelay_enabled && isset($iflist[$if])) {
508
	$pgtitle[] = $iflist[$if];
509
	$pgtitle[] = gettext("DHCPv6 Server");
510
}
511
$shortcut_section = "dhcp6";
512

    
513
include("head.inc");
514

    
515
if ($input_errors) {
516
	print_input_errors($input_errors);
517
}
518

    
519
if ($savemsg) {
520
	print_info_box($savemsg, 'success');
521
}
522

    
523
if ($dhcrelay_enabled) {
524
	print_info_box(gettext("DHCPv6 Relay is currently enabled. Cannot enable the DHCPv6 Server service while the DHCPv6 Relay is enabled on any interface."), 'danger', false);
525
	include("foot.inc");
526
	exit;
527
}
528

    
529
if (is_subsystem_dirty('staticmaps')) {
530
	print_apply_box(gettext('The static mapping configuration has been changed.') . '<br />' . gettext('You must apply the changes in order for them to take effect.'));
531
}
532

    
533
/* active tabs */
534
$tab_array = array();
535
$tabscounter = 0;
536
$i = 0;
537

    
538
foreach ($iflist as $ifent => $ifname) {
539
	$oc = $config['interfaces'][$ifent];
540
	$valid_if_ipaddrv6 = (bool) ($oc['ipaddrv6'] == 'track6' ||
541
	    (is_ipaddrv6($oc['ipaddrv6']) &&
542
	    !is_linklocal($oc['ipaddrv6'])));
543

    
544
	if ((!is_array($config['dhcpdv6'][$ifent]) ||
545
	    !isset($config['dhcpdv6'][$ifent]['enable'])) &&
546
	    !$valid_if_ipaddrv6) {
547
		continue;
548
	}
549

    
550
	if ($ifent == $if) {
551
		$active = true;
552
	} else {
553
		$active = false;
554
	}
555

    
556
	$tab_array[] = array($ifname, $active, "services_dhcpv6.php?if={$ifent}");
557
	$tabscounter++;
558
}
559

    
560
/* tack on PPPoE or PPtP servers here */
561
/* pppoe server */
562
if (is_array($config['pppoes']['pppoe'])) {
563
	foreach ($config['pppoes']['pppoe'] as $pppoe) {
564
		if ($pppoe['mode'] == "server") {
565
			$ifent = "poes". $pppoe['pppoeid'];
566
			$ifname = strtoupper($ifent);
567

    
568
			if ($ifent == $if) {
569
				$active = true;
570
			} else {
571
				$active = false;
572
			}
573

    
574
			$tab_array[] = array($ifname, $active, "services_dhcpv6.php?if={$ifent}");
575
			$tabscounter++;
576
		}
577
	}
578
}
579

    
580
if ($tabscounter == 0) {
581
	print_info_box(gettext("The DHCPv6 Server can only be enabled on interfaces configured with a static IPv6 address. This system has none."), 'danger');
582
	include("foot.inc");
583
	exit;
584
}
585

    
586
display_top_tabs($tab_array);
587

    
588
$tab_array = array();
589
$tab_array[] = array(gettext("DHCPv6 Server"),		 true,	"services_dhcpv6.php?if={$if}");
590
$tab_array[] = array(gettext("Router Advertisements"), false, "services_router_advertisements.php?if={$if}");
591
display_top_tabs($tab_array, false, 'nav nav-tabs');
592

    
593
$form = new Form();
594

    
595
$section = new Form_Section('DHCPv6 Options');
596

    
597
$section->addInput(new Form_Checkbox(
598
	'enable',
599
	'DHCPv6 Server',
600
	'Enable DHCPv6 server on interface ' . $iflist[$if],
601
	$pconfig['enable']
602
));
603

    
604
if (is_ipaddrv6($ifcfgip)) {
605

    
606
	if ($ifcfgip == "::") {
607
		$sntext = "Prefix Delegation";
608
	} else {
609
		$sntext = gen_subnetv6($ifcfgip, $ifcfgsn);
610
	}
611
	$section->addInput(new Form_StaticText(
612
		'Subnet',
613
		$sntext
614
		));
615

    
616
	$section->addInput(new Form_StaticText(
617
		'Subnet Mask',
618
		$ifcfgsn . ' bits'
619
		));
620

    
621
	$section->addInput(new Form_StaticText(
622
		'Available Range',
623
		$range_from = gen_subnetv6($ifcfgip, $ifcfgsn) . ' to ' . gen_subnetv6_max($ifcfgip, $ifcfgsn)
624
		))->setHelp($trackifname ? 'Prefix Delegation subnet will be appended to the beginning of the defined range':'');
625
}
626

    
627
if ($is_olsr_enabled) {
628
	$section->addInput(new Form_Select(
629
	'netmask',
630
	'Subnet Mask',
631
	$pconfig['netmask'],
632
	array_combine(range(128, 1, -1), range(128, 1, -1))
633
	));
634
}
635

    
636
$f1 = new Form_Input(
637
	'range_from',
638
	null,
639
	'text',
640
	$pconfig['range_from']
641
);
642

    
643
$f1->setHelp('From');
644

    
645
$f2 = new Form_Input(
646
	'range_to',
647
	null,
648
	'text',
649
	$pconfig['range_to']
650
);
651

    
652
$f2->setHelp('To');
653

    
654
$group = new Form_Group('Range');
655

    
656
$group->add($f1);
657
$group->add($f2);
658

    
659
$section->add($group);
660

    
661
$f1 = new Form_Input(
662
	'prefixrange_from',
663
	null,
664
	'text',
665
	$pconfig['prefixrange_from']
666
);
667

    
668
$f1->setHelp('From');
669

    
670
$f2 = new Form_Input(
671
	'prefixrange_to',
672
	null,
673
	'text',
674
	$pconfig['prefixrange_to']
675
);
676

    
677
$f2->setHelp('To');
678

    
679
$group = new Form_Group('Prefix Delegation Range');
680

    
681
$group->add($f1);
682
$group->add($f2);
683

    
684
$section->add($group);
685

    
686
$section->addInput(new Form_Select(
687
	'prefixrange_length',
688
	'Prefix Delegation Size',
689
	$pconfig['prefixrange_length'],
690
	array(
691
		'48' => '48',
692
		'52' => '52',
693
		'56' => '56',
694
		'60' => '60',
695
		'62' => '62',
696
		'63' => '63',
697
		'64' => '64'
698
		)
699
))->setHelp('You can define a Prefix range here for DHCP Prefix Delegation. This allows for assigning networks to subrouters. The start and end of the range must end on boundaries of the prefix delegation size.');
700

    
701
$group = new Form_Group('DNS Servers');
702

    
703
for ($i=1;$i<=4; $i++) {
704
	$group->add(new Form_input(
705
		'dns' . $i,
706
		null,
707
		'text',
708
		$pconfig['dns' . $i],
709
		['placeholder' => 'DNS ' . $i]
710
	));
711
}
712

    
713
$group->setHelp('Leave blank to use the system default DNS servers, this interface\'s IP if DNS forwarder is enabled, or the servers configured on the "General" page.');
714
$section->add($group);
715

    
716
$section->addInput(new Form_Input(
717
	'domain',
718
	'Domain Name',
719
	'text',
720
	$pconfig['domain']
721
))->setHelp('The default is to use the domain name of this system as the default domain name provided by DHCP. You may specify an alternate domain name here. ');
722

    
723
$section->addInput(new Form_Input(
724
	'domainsearchlist',
725
	'Domain search list',
726
	'text',
727
	$pconfig['domainsearchlist']
728
))->setHelp('The DHCP server can optionally provide a domain search list. Use the semicolon character as separator');
729

    
730
$section->addInput(new Form_Input(
731
	'deftime',
732
	'Default lease time',
733
	'text',
734
	$pconfig['deftime']
735
))->setHelp('Lease time in seconds. Used for clients that do not ask for a specific expiration time. ' . ' <br />' .
736
			'The default is 7200 seconds.');
737

    
738
$section->addInput(new Form_Input(
739
	'maxtime',
740
	'Max lease time',
741
	'text',
742
	$pconfig['maxtime']
743
))->setHelp('Maximum lease time for clients that ask for a specific expiration time.' . ' <br />' .
744
			'The default is 86400 seconds.');
745

    
746
$section->addInput(new Form_Checkbox(
747
	'dhcpv6leaseinlocaltime',
748
	'Time Format Change',
749
	'Change DHCPv6 display lease time from UTC to local time',
750
	$pconfig['dhcpv6leaseinlocaltime']
751
))->setHelp('By default DHCPv6 leases are displayed in UTC time. ' .
752
			'By checking this box DHCPv6 lease time will be displayed in local time and set to time zone selected. ' .
753
			'This will be used for all DHCPv6 interfaces lease time.');
754

    
755
$btndyndns = new Form_Button(
756
	'btndyndns',
757
	'Advanced',
758
	null,
759
	'fa-cog'
760
);
761

    
762
$btndyndns->addClass('btn-info btn-sm');
763

    
764
$section->addInput(new Form_StaticText(
765
	'Dynamic DNS',
766
	$btndyndns
767
));
768

    
769
$section->addInput(new Form_Checkbox(
770
	'ddnsupdate',
771
	'DHCP Registration',
772
	'Enable registration of DHCP client names in DNS.',
773
	$pconfig['ddnsupdate']
774
));
775

    
776
$section->addInput(new Form_Input(
777
	'ddnsdomain',
778
	'DDNS Domain',
779
	'text',
780
	$pconfig['ddnsdomain']
781
))->setHelp('Leave blank to disable dynamic DNS registration. Enter the dynamic DNS domain which will be used to register client names in the DNS server.');
782

    
783
$section->addInput(new Form_IpAddress(
784
	'ddnsdomainprimary',
785
	'DDNS Server IP',
786
	$pconfig['ddnsdomainprimary']
787
))->setHelp('Enter the primary domain name server IP address for the dynamic domain name.');
788

    
789
$section->addInput(new Form_Input(
790
	'ddnsdomainkeyname',
791
	'DDNS Domain Key name',
792
	'text',
793
	$pconfig['ddnsdomainkeyname']
794
))->setHelp('Enter the dynamic DNS domain key name which will be used to register client names in the DNS server.');
795

    
796
$section->addInput(new Form_Input(
797
	'ddnsdomainkey',
798
	'DDNS Domain Key secret',
799
	'text',
800
	$pconfig['ddnsdomainkey']
801
))->setHelp('Enter the dynamic DNS domain key secret which will be used to register client names in the DNS server.');
802

    
803
$section->addInput(new Form_Select(
804
	'ddnsclientupdates',
805
	'DDNS Client Updates',
806
	$pconfig['ddnsclientupdates'],
807
	array(
808
	    'allow' => gettext('Allow'),
809
	    'deny' => gettext('Deny'),
810
	    'ignore' => gettext('Ignore'))
811
))->setHelp('How Forward entries are handled when client indicates they wish to update DNS.  ' .
812
	    'Allow prevents DHCP from updating Forward entries, Deny indicates that DHCP will ' .
813
	    'do the updates and the client should not, Ignore specifies that DHCP will do the ' .
814
	    'update and the client can also attempt the update usually using a different domain name.');
815

    
816
$section->addInput(new Form_Checkbox(
817
	'ddnsreverse',
818
	'DDNS Reverse',
819
	'Add reverse dynamic DNS entries.',
820
	$pconfig['ddnsreverse']
821
));
822

    
823
$btnntp = new Form_Button(
824
	'btnntp',
825
	'Advanced',
826
	null,
827
	'fa-cog'
828
);
829

    
830
$btnntp->addClass('btn-info btn-sm');
831

    
832
$section->addInput(new Form_StaticText(
833
	'NTP servers',
834
	$btnntp
835
));
836

    
837
$group = new Form_Group('NTP Servers');
838

    
839
$group->add(new Form_Input(
840
	'ntp1',
841
	'NTP Server 1',
842
	'text',
843
	$pconfig['ntp1'],
844
	['placeholder' => 'NTP 1']
845
));
846

    
847
$group->add(new Form_Input(
848
	'ntp2',
849
	'NTP Server 2',
850
	'text',
851
	$pconfig['ntp2'],
852
	['placeholder' => 'NTP 2']
853
));
854

    
855
$group->addClass('ntpclass');
856

    
857
$section->add($group);
858

    
859
$btnldap = new Form_Button(
860
	'btnldap',
861
	'Advanced',
862
	null,
863
	'fa-cog'
864
);
865

    
866
$btnldap->addClass('btn-info btn-sm');
867

    
868
$section->addInput(new Form_StaticText(
869
	'LDAP',
870
	$btnldap
871
));
872

    
873
$section->addInput(new Form_Input(
874
	'ldap',
875
	'LDAP URI',
876
	'text',
877
	$pconfig['ldap']
878
));
879

    
880
$btnnetboot = new Form_Button(
881
	'btnnetboot',
882
	'Advanced',
883
	null,
884
	'fa-cog'
885
);
886

    
887
$btnnetboot->addClass('btn-info btn-sm');
888

    
889
$section->addInput(new Form_StaticText(
890
	'Network booting',
891
	$btnnetboot
892
));
893

    
894
$section->addInput(new Form_Checkbox(
895
	'shownetboot',
896
	'Network booting',
897
	'Enable Network Booting',
898
	$pconfig['shownetboot']
899
));
900

    
901
$section->addInput(new Form_Input(
902
	'bootfile_url',
903
	'Bootfile URL',
904
	'text',
905
	$pconfig['bootfile_url']
906
));
907

    
908
$btnadnl = new Form_Button(
909
	'btnadnl',
910
	'Advanced',
911
	null,
912
	'fa-cog'
913
);
914

    
915
$btnadnl->addClass('btn-info btn-sm');
916

    
917
$section->addInput(new Form_StaticText(
918
	'Additional BOOTP/DHCP Options',
919
	$btnadnl
920
));
921

    
922
$form->add($section);
923

    
924
$title = 'Show Additional BOOTP/DHCP Options';
925

    
926
if (!$pconfig['numberoptions']) {
927
	$noopts = true;
928
	$pconfig['numberoptions']['item'] = array(0 => array('number' => "", 'value' => ""));
929
} else {
930
	$noopts = false;
931
}
932

    
933
$counter = 0;
934
$last = count($pconfig['numberoptions']['item']) - 1;
935

    
936
foreach ($pconfig['numberoptions']['item'] as $item) {
937
	$group = new Form_Group(null);
938
	$group->addClass('repeatable');
939
	$group->addClass('adnloptions');
940

    
941
	$group->add(new Form_Input(
942
		'number' . $counter,
943
		null,
944
		'text',
945
		$item['number']
946
	))->setHelp($counter == $last ? 'Number':null);
947

    
948
	$group->add(new Form_Input(
949
		'value' . $counter,
950
		null,
951
		'text',
952
		base64_decode($item['value'])
953
	))->setHelp($counter == $last ? 'Value':null);
954

    
955
	$btn = new Form_Button(
956
		'deleterow' . $counter,
957
		'Delete',
958
		null,
959
		'fa-trash'
960
	);
961

    
962
	$btn->addClass('btn-warning');
963
	$group->add($btn);
964
	$section->add($group);
965
	$counter++;
966
}
967

    
968

    
969
$btnaddopt = new Form_Button(
970
	'addrow',
971
	'Add Option',
972
	null,
973
	'fa-plus'
974
);
975

    
976
$btnaddopt->removeClass('btn-primary')->addClass('btn-success btn-sm');
977

    
978
$section->addInput($btnaddopt);
979

    
980
$section->addInput(new Form_Input(
981
	'if',
982
	null,
983
	'hidden',
984
	$if
985
));
986

    
987
print($form);
988

    
989
?>
990
<div class="infoblock blockopen">
991
<?php
992
print_info_box(
993
	sprintf(
994
		gettext('The DNS servers entered in %1$sSystem: General setup%3$s (or the %2$sDNS forwarder%3$s if enabled) will be assigned to clients by the DHCP server.'),
995
		'<a href="system.php">',
996
		'<a href="services_dnsmasq.php"/>',
997
		'</a>') .
998
	'<br />' .
999
	sprintf(
1000
		gettext('The DHCP lease table can be viewed on the %1$sStatus: DHCPv6 leases%2$s page.'),
1001
		'<a href="status_dhcpv6_leases.php">',
1002
		'</a>'),
1003
	'info',
1004
	false);
1005
?>
1006
</div>
1007
<div class="panel panel-default">
1008
	<div class="panel-heading"><h2 class="panel-title"><?=gettext("DHCPv6 Static Mappings for this Interface");?></h2></div>
1009
	<div class="panel-body table-responsive">
1010
		<table class="table table-striped table-hover table-condensed">
1011
			<thead>
1012
				<tr>
1013
					<th><?=gettext("DUID")?></th>
1014
					<th><?=gettext("IPv6 address")?></th>
1015
					<th><?=gettext("Hostname")?></th>
1016
					<th><?=gettext("Description")?></th>
1017
					<th><!-- Buttons --></th>
1018
				</tr>
1019
			</thead>
1020
			<tbody>
1021
<?php
1022
if (is_array($a_maps)):
1023
	$i = 0;
1024
	foreach ($a_maps as $mapent):
1025
		if ($mapent['duid'] != "" or $mapent['ipaddrv6'] != ""):
1026
?>
1027
				<tr>
1028
					<td>
1029
						<?=htmlspecialchars($mapent['duid'])?>
1030
					</td>
1031
					<td>
1032
						<?=htmlspecialchars($mapent['ipaddrv6'])?>
1033
					</td>
1034
					<td>
1035
						<?=htmlspecialchars($mapent['hostname'])?>
1036
					</td>
1037
					<td>
1038
						<?=htmlspecialchars($mapent['descr'])?>
1039
					</td>
1040
					<td>
1041
						<a class="fa fa-pencil"	title="<?=gettext('Edit static mapping')?>" href="services_dhcpv6_edit.php?if=<?=$if?>&amp;id=<?=$i?>"></a>
1042
						<a class="fa fa-trash"	title="<?=gettext('Delete static mapping')?>" href="services_dhcpv6.php?if=<?=$if?>&amp;act=del&amp;id=<?=$i?>"></a>
1043
					</td>
1044
				</tr>
1045
<?php
1046
		endif;
1047
	$i++;
1048
	endforeach;
1049
endif;
1050
?>
1051
			</tbody>
1052
		</table>
1053
	</div>
1054
</div>
1055

    
1056
<nav class="action-buttons">
1057
	<a href="services_dhcpv6_edit.php?if=<?=$if?>" class="btn btn-sm btn-success"/>
1058
		<i class="fa fa-plus icon-embed-btn"></i>
1059
		<?=gettext("Add")?>
1060
	</a>
1061
</nav>
1062

    
1063
<script type="text/javascript">
1064
//<![CDATA[
1065
events.push(function() {
1066

    
1067
	function hideDDNS(hide) {
1068
		hideCheckbox('ddnsupdate', hide);
1069
		hideInput('ddnsdomain', hide);
1070
		hideInput('ddnsdomainprimary', hide);
1071
		hideInput('ddnsdomainkeyname', hide);
1072
		hideInput('ddnsdomainkey', hide);
1073
		hideInput('ddnsclientupdates', hide);
1074
		hideCheckbox('ddnsreverse', hide);
1075
	}
1076

    
1077
	// Make the 'Copy My MAC' button a plain button, not a submit button
1078
	$("#btnmymac").prop('type','button');
1079

    
1080
	// On click, copy the hidden 'mymac' text to the 'mac' input
1081
	$("#btnmymac").click(function() {
1082
		$('#mac').val('<?=$mymac?>');
1083
	});
1084

    
1085
	// Make the 'tftp' button a plain button, not a submit button
1086
	$("#btntftp").prop('type','button');
1087

    
1088
	// Show tftp controls
1089
	$("#btntftp").click(function() {
1090
		hideInput('tftp', false);
1091
	});
1092

    
1093
	// Make the 'ntp' button a plain button, not a submit button
1094
	$("#btnntp").prop('type','button');
1095

    
1096
	// Show ntp controls
1097
	$("#btnntp").click(function() {
1098
		hideClass('ntpclass', false);
1099
	});
1100

    
1101
	// Make the 'ddns' button a plain button, not a submit button
1102
	$("#btndyndns").prop('type','button');
1103

    
1104
	// Show ddns controls
1105
	$("#btndyndns").click(function() {
1106
		hideDDNS(false);
1107
	});
1108

    
1109
	// Make the 'ldap' button a plain button, not a submit button
1110
	$("#btnldap").prop('type','button');
1111

    
1112
	// Show ldap controls
1113
	$("#btnldap").click(function() {
1114
		hideInput('ldap', false);
1115
	});
1116

    
1117
	// Make the 'netboot' button a plain button, not a submit button
1118
	$("#btnnetboot").prop('type','button');
1119

    
1120
	// Show netboot controls
1121
	$("#btnnetboot").click(function() {
1122
		hideInput('bootfile_url', false);
1123
		hideCheckbox('shownetboot', false);
1124
	});
1125

    
1126
	// Make the 'additional options' button a plain button, not a submit button
1127
	$("#btnadnl").prop('type','button');
1128

    
1129
	// Show additional  controls
1130
	$("#btnadnl").click(function() {
1131
		hideClass('adnloptions', false);
1132
		hideInput('addrow', false);
1133
		checkLastRow();
1134
	});
1135

    
1136
	$('#enable').click(function() {
1137
	    do_toggle();
1138
	});
1139

    
1140
	function do_toggle() {
1141
		if ($('#enable').prop('checked')) {
1142
			$('.form-group:not(:first-child)').show();
1143
			hideClass('adnloptions', <?php echo json_encode($noopts); ?>);
1144
			hideInput('addrow', <?php echo json_encode($noopts); ?>);
1145
		} else {
1146
			$('.form-group:not(:first-child)').hide();
1147
		}
1148
	}
1149

    
1150
	// On initial load
1151
	do_toggle();
1152
	hideDDNS(true);
1153
	hideClass('ntpclass', true);
1154
	hideInput('tftp', true);
1155
	hideInput('ldap', true);
1156
	hideInput('bootfile_url', true);
1157
	hideCheckbox('shownetboot', true);
1158
	if ($('#enable').prop('checked')) {
1159
		hideClass('adnloptions', <?php echo json_encode($noopts); ?>);
1160
		hideInput('addrow', <?php echo json_encode($noopts); ?>);
1161
	} else {
1162
		hideClass('adnloptions', true);
1163
		hideInput('addrow', true);
1164
	}
1165

    
1166
});
1167
//]]>
1168
</script>
1169

    
1170
<?php include('foot.inc');
(121-121/227)