Project

General

Profile

Download (36.7 KB) Statistics
| Branch: | Tag: | Revision:
1
<?php
2
/*
3
 * services_dhcpv6.php
4
 *
5
 * part of pfSense (https://www.pfsense.org)
6
 * Copyright (c) 2004-2016 Rubicon Communications, LLC (Netgate)
7
 * Copyright (c) 2010 Seth Mos <seth.mos@dds.nl>
8
 * All rights reserved.
9
 *
10
 * originally based on m0n0wall (http://m0n0.ch/wall)
11
 * Copyright (c) 2003-2004 Manuel Kasper <mk@neon1.net>.
12
 * All rights reserved.
13
 *
14
 * Licensed under the Apache License, Version 2.0 (the "License");
15
 * you may not use this file except in compliance with the License.
16
 * You may obtain a copy of the License at
17
 *
18
 * http://www.apache.org/licenses/LICENSE-2.0
19
 *
20
 * Unless required by applicable law or agreed to in writing, software
21
 * distributed under the License is distributed on an "AS IS" BASIS,
22
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
23
 * See the License for the specific language governing permissions and
24
 * limitations under the License.
25
 */
26

    
27
##|+PRIV
28
##|*IDENT=page-services-dhcpv6server
29
##|*NAME=Services: DHCPv6 Server
30
##|*DESCR=Allow access to the 'Services: DHCPv6 Server' page.
31
##|*MATCH=services_dhcpv6.php*
32
##|-PRIV
33

    
34
require_once("guiconfig.inc");
35
require_once("filter.inc");
36

    
37
function dhcpv6_apply_changes($dhcpdv6_enable_changed) {
38
	$retval = 0;
39
	$retvaldhcp = 0;
40
	$retvaldns = 0;
41
	/* Stop DHCPv6 so we can cleanup leases */
42
	killbypid("{$g['dhcpd_chroot_path']}{$g['varrun_path']}/dhcpdv6.pid");
43
	// dhcp_clean_leases();
44
	/* dnsmasq_configure calls dhcpd_configure */
45
	/* no need to restart dhcpd twice */
46
	if (isset($config['dnsmasq']['enable']) && isset($config['dnsmasq']['regdhcpstatic']))	{
47
		$retvaldns |= services_dnsmasq_configure();
48
		if ($retvaldns == 0) {
49
			clear_subsystem_dirty('hosts');
50
			clear_subsystem_dirty('staticmaps');
51
		}
52
	} else if (isset($config['unbound']['enable']) && isset($config['unbound']['regdhcpstatic'])) {
53
		$retvaldns |= services_unbound_configure();
54
		if ($retvaldns == 0) {
55
			clear_subsystem_dirty('unbound');
56
			clear_subsystem_dirty('staticmaps');
57
		}
58
	} else {
59
		$retvaldhcp |= services_dhcpd_configure();
60
		if ($retvaldhcp == 0) {
61
			clear_subsystem_dirty('staticmaps');
62
		}
63
	}
64
	if ($dhcpdv6_enable_changed) {
65
		$retvalfc |= filter_configure();
66
	}
67
	if ($retvaldhcp == 1 || $retvaldns == 1 || $retvalfc == 1) {
68
		$retval = 1;
69
	}
70
	return $retval;
71
}
72

    
73
if (!$g['services_dhcp_server_enable']) {
74
	header("Location: /");
75
	exit;
76
}
77

    
78
$if = $_GET['if'];
79
if ($_POST['if']) {
80
	$if = $_POST['if'];
81
}
82

    
83
/* if OLSRD is enabled, allow WAN to house DHCP. */
84
if ($config['installedpackages']['olsrd']) {
85
	foreach ($config['installedpackages']['olsrd']['config'] as $olsrd) {
86
		if ($olsrd['enable']) {
87
			$is_olsr_enabled = true;
88
			break;
89
		}
90
	}
91
}
92

    
93
$iflist = get_configured_interface_with_descr();
94
$iflist = array_merge($iflist, get_configured_pppoe_server_interfaces());
95

    
96
/* set the starting interface */
97
if (!$if || !isset($iflist[$if])) {
98
	foreach ($iflist as $ifent => $ifname) {
99
		$oc = $config['interfaces'][$ifent];
100
		$valid_if_ipaddrv6 = (bool) ($oc['ipaddrv6'] == 'track6' ||
101
		    (is_ipaddrv6($oc['ipaddrv6']) &&
102
		    !is_linklocal($oc['ipaddrv6'])));
103

    
104
		if ((!is_array($config['dhcpdv6'][$ifent]) ||
105
		    !isset($config['dhcpdv6'][$ifent]['enable'])) &&
106
		    !$valid_if_ipaddrv6) {
107
			continue;
108
		}
109
		$if = $ifent;
110
		break;
111
	}
112
}
113

    
114
if (is_array($config['dhcpdv6'][$if])) {
115
	/* DHCPv6 */
116
	if (is_array($config['dhcpdv6'][$if]['range'])) {
117
		$pconfig['range_from'] = $config['dhcpdv6'][$if]['range']['from'];
118
		$pconfig['range_to'] = $config['dhcpdv6'][$if]['range']['to'];
119
	}
120
	if (is_array($config['dhcpdv6'][$if]['prefixrange'])) {
121
		$pconfig['prefixrange_from'] = $config['dhcpdv6'][$if]['prefixrange']['from'];
122
		$pconfig['prefixrange_to'] = $config['dhcpdv6'][$if]['prefixrange']['to'];
123
		$pconfig['prefixrange_length'] = $config['dhcpdv6'][$if]['prefixrange']['prefixlength'];
124
	}
125
	$pconfig['deftime'] = $config['dhcpdv6'][$if]['defaultleasetime'];
126
	$pconfig['maxtime'] = $config['dhcpdv6'][$if]['maxleasetime'];
127
	$pconfig['domain'] = $config['dhcpdv6'][$if]['domain'];
128
	$pconfig['domainsearchlist'] = $config['dhcpdv6'][$if]['domainsearchlist'];
129
	list($pconfig['wins1'], $pconfig['wins2']) = $config['dhcpdv6'][$if]['winsserver'];
130
	list($pconfig['dns1'], $pconfig['dns2'], $pconfig['dns3'], $pconfig['dns4']) = $config['dhcpdv6'][$if]['dnsserver'];
131
	$pconfig['enable'] = isset($config['dhcpdv6'][$if]['enable']);
132
	$pconfig['ddnsdomain'] = $config['dhcpdv6'][$if]['ddnsdomain'];
133
	$pconfig['ddnsdomainprimary'] = $config['dhcpdv6'][$if]['ddnsdomainprimary'];
134
	$pconfig['ddnsdomainkeyname'] = $config['dhcpdv6'][$if]['ddnsdomainkeyname'];
135
	$pconfig['ddnsdomainkey'] = $config['dhcpdv6'][$if]['ddnsdomainkey'];
136
	$pconfig['ddnsupdate'] = isset($config['dhcpdv6'][$if]['ddnsupdate']);
137
	$pconfig['ddnsforcehostname'] = isset($config['dhcpdv6'][$if]['ddnsforcehostname']);
138
	$pconfig['ddnsreverse'] = isset($config['dhcpdv6'][$if]['ddnsreverse']);
139
	$pconfig['ddnsclientupdates'] = $config['dhcpdv6'][$if]['ddnsclientupdates'];
140
	list($pconfig['ntp1'], $pconfig['ntp2']) = $config['dhcpdv6'][$if]['ntpserver'];
141
	$pconfig['tftp'] = $config['dhcpdv6'][$if]['tftp'];
142
	$pconfig['ldap'] = $config['dhcpdv6'][$if]['ldap'];
143
	$pconfig['netboot'] = isset($config['dhcpdv6'][$if]['netboot']);
144
	$pconfig['bootfile_url'] = $config['dhcpdv6'][$if]['bootfile_url'];
145
	$pconfig['netmask'] = $config['dhcpdv6'][$if]['netmask'];
146
	$pconfig['numberoptions'] = $config['dhcpdv6'][$if]['numberoptions'];
147
	$pconfig['dhcpv6leaseinlocaltime'] = $config['dhcpdv6'][$if]['dhcpv6leaseinlocaltime'];
148
	if (!is_array($config['dhcpdv6'][$if]['staticmap'])) {
149
		$config['dhcpdv6'][$if]['staticmap'] = array();
150
	}
151
	$a_maps = &$config['dhcpdv6'][$if]['staticmap'];
152
}
153

    
154
if ($config['interfaces'][$if]['ipaddrv6'] == 'track6') {
155
	$trackifname = $config['interfaces'][$if]['track6-interface'];
156
	$trackcfg = $config['interfaces'][$trackifname];
157
	$ifcfgsn = "64";
158
	$ifcfgip = '::';
159

    
160
	$str_help_mask = dhcpv6_pd_str_help($ifcfgsn);
161
} else {
162
	$ifcfgip = get_interface_ipv6($if);
163
	$ifcfgsn = get_interface_subnetv6($if);
164
}
165

    
166
/*	 set the enabled flag which will tell us if DHCP relay is enabled
167
 *	 on any interface. We will use this to disable DHCP server since
168
 *	 the two are not compatible with each other.
169
 */
170

    
171
$dhcrelay_enabled = false;
172
$dhcrelaycfg = $config['dhcrelay6'];
173

    
174
if (is_array($dhcrelaycfg) && isset($dhcrelaycfg['enable']) && isset($dhcrelaycfg['interface']) && !empty($dhcrelaycfg['interface'])) {
175
	$dhcrelayifs = explode(",", $dhcrelaycfg['interface']);
176

    
177
	foreach ($dhcrelayifs as $dhcrelayif) {
178

    
179
		if (isset($iflist[$dhcrelayif]) && (!link_interface_to_bridge($dhcrelayif))) {
180
			$dhcrelay_enabled = true;
181
			break;
182
		}
183
	}
184
}
185

    
186
if (isset($_POST['apply'])) {
187
	$changes_applied = true;
188
	$retval = dhcpv6_apply_changes(false);
189
} elseif (isset($_POST['save'])) {
190
	unset($input_errors);
191

    
192
	$old_dhcpdv6_enable = ($pconfig['enable'] == true);
193
	$new_dhcpdv6_enable = ($_POST['enable'] ? true : false);
194
	$dhcpdv6_enable_changed = ($old_dhcpdv6_enable != $new_dhcpdv6_enable);
195

    
196
	$pconfig = $_POST;
197

    
198
	$numberoptions = array();
199
	for ($x = 0; $x < 99; $x++) {
200
		if (isset($_POST["number{$x}"]) && ctype_digit($_POST["number{$x}"])) {
201
			$numbervalue = array();
202
			$numbervalue['number'] = htmlspecialchars($_POST["number{$x}"]);
203
			$numbervalue['value'] = base64_encode($_POST["value{$x}"]);
204
			$numberoptions['item'][] = $numbervalue;
205
		}
206
	}
207
	// Reload the new pconfig variable that the form uses.
208
	$pconfig['numberoptions'] = $numberoptions;
209

    
210
	/* input validation */
211

    
212
	// Note: if DHCPv6 Server is not enabled, then it is OK to adjust other parameters without specifying range from-to.
213
	if ($_POST['enable']) {
214
		$reqdfields = explode(" ", "range_from range_to");
215
		$reqdfieldsn = array(gettext("Range begin"), gettext("Range end"));
216

    
217
		do_input_validation($_POST, $reqdfields, $reqdfieldsn, $input_errors);
218
	}
219

    
220
	if (($_POST['prefixrange_from'] && !is_ipaddrv6($_POST['prefixrange_from']))) {
221
		$input_errors[] = gettext("A valid prefix range must be specified.");
222
	}
223
	if (($_POST['prefixrange_to'] && !is_ipaddrv6($_POST['prefixrange_to']))) {
224
		$input_errors[] = gettext("A valid prefix range must be specified.");
225
	}
226

    
227
	if ($_POST['prefixrange_from'] && $_POST['prefixrange_to'] &&
228
		$_POST['prefixrange_length']) {
229
		$netmask = Net_IPv6::getNetmask($_POST['prefixrange_from'],
230
			$_POST['prefixrange_length']);
231
		$netmask = Net_IPv6::compress($netmask);
232

    
233
		if ($netmask != Net_IPv6::compress(strtolower(
234
			$_POST['prefixrange_from']))) {
235
			$input_errors[] = sprintf(gettext(
236
				"Prefix Delegation From address is not a valid IPv6 Netmask for %s"),
237
				$netmask . '/' . $_POST['prefixrange_length']);
238
		}
239

    
240
		$netmask = Net_IPv6::getNetmask($_POST['prefixrange_to'],
241
			$_POST['prefixrange_length']);
242
		$netmask = Net_IPv6::compress($netmask);
243

    
244
		if ($netmask != Net_IPv6::compress(strtolower(
245
			$_POST['prefixrange_to']))) {
246
			$input_errors[] = sprintf(gettext(
247
				"Prefix Delegation To address is not a valid IPv6 Netmask for %s"),
248
				$netmask . '/' . $_POST['prefixrange_length']);
249
		}
250
	}
251

    
252
	$range_from_to_ok = true;
253

    
254
	if ($_POST['range_from']) {
255
		if (!is_ipaddrv6($_POST['range_from'])) {
256
			$input_errors[] = gettext("A valid range must be specified.");
257
			$range_from_to_ok = false;
258
		} elseif ($config['interfaces'][$if]['ipaddrv6'] == 'track6' &&
259
			!Net_IPv6::isInNetmask($_POST['range_from'], '::', $ifcfgsn)) {
260
			$input_errors[] = sprintf(gettext(
261
				"The prefix (upper %s bits) must be zero.  Use the form %s"),
262
				$ifcfgsn, $str_help_mask);
263
			$range_from_to_ok = false;
264
		}
265
	}
266
	if ($_POST['range_to']) {
267
		if (!is_ipaddrv6($_POST['range_to'])) {
268
			$input_errors[] = gettext("A valid range must be specified.");
269
			$range_from_to_ok = false;
270
		} elseif ($config['interfaces'][$if]['ipaddrv6'] == 'track6' &&
271
			!Net_IPv6::isInNetmask($_POST['range_to'], '::', $ifcfgsn)) {
272
			$input_errors[] = sprintf(gettext(
273
				"The prefix (upper %s bits) must be zero.  Use the form %s"),
274
				$ifcfgsn, $str_help_mask);
275
			$range_from_to_ok = false;
276
		}
277
	}
278
	if (($_POST['range_from'] && !$_POST['range_to']) || ($_POST['range_to'] && !$_POST['range_from'])) {
279
		$input_errors[] = gettext("Range From and Range To must both be entered.");
280
	}
281
	if (($_POST['gateway'] && !is_ipaddrv6($_POST['gateway']))) {
282
		$input_errors[] = gettext("A valid IPv6 address must be specified for the gateway.");
283
	}
284
	if (($_POST['dns1'] && !is_ipaddrv6($_POST['dns1'])) ||
285
		($_POST['dns2'] && !is_ipaddrv6($_POST['dns2'])) ||
286
		($_POST['dns3'] && !is_ipaddrv6($_POST['dns3'])) ||
287
		($_POST['dns4'] && !is_ipaddrv6($_POST['dns4']))) {
288
		$input_errors[] = gettext("A valid IPv6 address must be specified for each of the DNS servers.");
289
	}
290

    
291
	if ($_POST['deftime'] && (!is_numeric($_POST['deftime']) || ($_POST['deftime'] < 60))) {
292
		$input_errors[] = gettext("The default lease time must be at least 60 seconds.");
293
	}
294
	if ($_POST['maxtime'] && (!is_numeric($_POST['maxtime']) || ($_POST['maxtime'] < 60) || ($_POST['maxtime'] <= $_POST['deftime']))) {
295
		$input_errors[] = gettext("The maximum lease time must be at least 60 seconds and higher than the default lease time.");
296
	}
297
	if (($_POST['ddnsdomain'] && !is_domain($_POST['ddnsdomain']))) {
298
		$input_errors[] = gettext("A valid domain name must be specified for the dynamic DNS registration.");
299
	}
300
	if (($_POST['ddnsdomain'] && !is_ipaddrv4($_POST['ddnsdomainprimary']))) {
301
		$input_errors[] = gettext("A valid primary domain name server IPv4 address must be specified for the dynamic domain name.");
302
	}
303
	if (($_POST['ddnsdomainkey'] && !$_POST['ddnsdomainkeyname']) ||
304
		($_POST['ddnsdomainkeyname'] && !$_POST['ddnsdomainkey'])) {
305
		$input_errors[] = gettext("Both a valid domain key and key name must be specified.");
306
	}
307
	if ($_POST['domainsearchlist']) {
308
		$domain_array=preg_split("/[ ;]+/", $_POST['domainsearchlist']);
309
		foreach ($domain_array as $curdomain) {
310
			if (!is_domain($curdomain)) {
311
				$input_errors[] = gettext("A valid domain search list must be specified.");
312
				break;
313
			}
314
		}
315
	}
316

    
317
	if (($_POST['ntp1'] && !is_ipaddrv6($_POST['ntp1'])) || ($_POST['ntp2'] && !is_ipaddrv6($_POST['ntp2']))) {
318
		$input_errors[] = gettext("A valid IPv6 address must be specified for the primary/secondary NTP servers.");
319
	}
320
	if (($_POST['domain'] && !is_domain($_POST['domain']))) {
321
		$input_errors[] = gettext("A valid domain name must be specified for the DNS domain.");
322
	}
323
	if ($_POST['tftp'] && !is_ipaddr($_POST['tftp']) && !is_domain($_POST['tftp']) && !is_URL($_POST['tftp'])) {
324
		$input_errors[] = gettext("A valid IPv6 address or hostname must be specified for the TFTP server.");
325
	}
326
	if (($_POST['bootfile_url'] && !is_URL($_POST['bootfile_url']))) {
327
		$input_errors[] = gettext("A valid URL must be specified for the network bootfile.");
328
	}
329

    
330
	// Disallow a range that includes the virtualip
331
	if ($range_from_to_ok && is_array($config['virtualip']['vip'])) {
332
		foreach ($config['virtualip']['vip'] as $vip) {
333
			if ($vip['interface'] == $if) {
334
				if ($vip['subnetv6'] && is_inrange_v6($vip['subnetv6'], $_POST['range_from'], $_POST['range_to'])) {
335
					$input_errors[] = sprintf(gettext("The subnet range cannot overlap with virtual IPv6 address %s."), $vip['subnetv6']);
336
				}
337
			}
338
		}
339
	}
340

    
341
	$noip = false;
342
	if (is_array($a_maps)) {
343
		foreach ($a_maps as $map) {
344
			if (empty($map['ipaddrv6'])) {
345
				$noip = true;
346
			}
347
		}
348
	}
349

    
350
	/* make sure that the DHCP Relay isn't enabled on this interface */
351
	if ($_POST['enable'] && $dhcrelay_enabled) {
352
		$input_errors[] = sprintf(gettext("The DHCP relay on the %s interface must be disabled before enabling the DHCP server."), $iflist[$if]);
353
	}
354

    
355
	// If nothing is wrong so far, and we have range from and to, then check conditions related to the values of range from and to.
356
	if (!$input_errors && $_POST['range_from'] && $_POST['range_to']) {
357
		/* make sure the range lies within the current subnet */
358
		$subnet_start = gen_subnetv6($ifcfgip, $ifcfgsn);
359
		$subnet_end = gen_subnetv6_max($ifcfgip, $ifcfgsn);
360

    
361
		if (is_ipaddrv6($ifcfgip)) {
362
			if ((!is_inrange_v6($_POST['range_from'], $subnet_start, $subnet_end)) ||
363
				(!is_inrange_v6($_POST['range_to'], $subnet_start, $subnet_end))) {
364
				$input_errors[] = gettext("The specified range lies outside of the current subnet.");
365
			}
366
		}
367
		/* "from" cannot be higher than "to" */
368
		if (inet_pton($_POST['range_from']) > inet_pton($_POST['range_to'])) {
369
			$input_errors[] = gettext("The range is invalid (first element higher than second element).");
370
		}
371

    
372
		/* Verify static mappings do not overlap:
373
		   - available DHCP range
374
		   - prefix delegation range (FIXME: still need to be completed) */
375
		$dynsubnet_start = inet_pton($_POST['range_from']);
376
		$dynsubnet_end = inet_pton($_POST['range_to']);
377

    
378
		if (is_array($a_maps)) {
379
			foreach ($a_maps as $map) {
380
				if (empty($map['ipaddrv6'])) {
381
					continue;
382
				}
383
				if ((inet_pton($map['ipaddrv6']) > $dynsubnet_start) &&
384
					(inet_pton($map['ipaddrv6']) < $dynsubnet_end)) {
385
					$input_errors[] = sprintf(gettext("The DHCP range cannot overlap any static DHCP mappings."));
386
					break;
387
				}
388
			}
389
		}
390
	}
391

    
392
	if (!$input_errors) {
393
		if (!is_array($config['dhcpdv6'][$if])) {
394
			$config['dhcpdv6'][$if] = array();
395
		}
396
		if (!is_array($config['dhcpdv6'][$if]['range'])) {
397
			$config['dhcpdv6'][$if]['range'] = array();
398
		}
399
		if (!is_array($config['dhcpdv6'][$if]['prefixrange'])) {
400
			$config['dhcpdv6'][$if]['prefixrange'] = array();
401
		}
402

    
403
		$config['dhcpdv6'][$if]['range']['from'] = $_POST['range_from'];
404
		$config['dhcpdv6'][$if]['range']['to'] = $_POST['range_to'];
405
		$config['dhcpdv6'][$if]['prefixrange']['from'] = $_POST['prefixrange_from'];
406
		$config['dhcpdv6'][$if]['prefixrange']['to'] = $_POST['prefixrange_to'];
407
		$config['dhcpdv6'][$if]['prefixrange']['prefixlength'] = $_POST['prefixrange_length'];
408
		$config['dhcpdv6'][$if]['defaultleasetime'] = $_POST['deftime'];
409
		$config['dhcpdv6'][$if]['maxleasetime'] = $_POST['maxtime'];
410
		$config['dhcpdv6'][$if]['netmask'] = $_POST['netmask'];
411

    
412
		unset($config['dhcpdv6'][$if]['winsserver']);
413

    
414
		unset($config['dhcpdv6'][$if]['dnsserver']);
415
		if ($_POST['dns1']) {
416
			$config['dhcpdv6'][$if]['dnsserver'][] = $_POST['dns1'];
417
		}
418
		if ($_POST['dns2']) {
419
			$config['dhcpdv6'][$if]['dnsserver'][] = $_POST['dns2'];
420
		}
421
		if ($_POST['dns3']) {
422
			$config['dhcpdv6'][$if]['dnsserver'][] = $_POST['dns3'];
423
		}
424
		if ($_POST['dns4']) {
425
			$config['dhcpdv6'][$if]['dnsserver'][] = $_POST['dns4'];
426
		}
427

    
428
		$config['dhcpdv6'][$if]['domain'] = $_POST['domain'];
429
		$config['dhcpdv6'][$if]['domainsearchlist'] = $_POST['domainsearchlist'];
430
		$config['dhcpdv6'][$if]['enable'] = ($_POST['enable']) ? true : false;
431
		$config['dhcpdv6'][$if]['ddnsdomain'] = $_POST['ddnsdomain'];
432
		$config['dhcpdv6'][$if]['ddnsdomainprimary'] = $_POST['ddnsdomainprimary'];
433
		$config['dhcpdv6'][$if]['ddnsdomainkeyname'] = $_POST['ddnsdomainkeyname'];
434
		$config['dhcpdv6'][$if]['ddnsdomainkey'] = $_POST['ddnsdomainkey'];
435
		$config['dhcpdv6'][$if]['ddnsupdate'] = ($_POST['ddnsupdate']) ? true : false;
436
		$config['dhcpdv6'][$if]['ddnsforcehostname'] = ($_POST['ddnsforcehostname']) ? true : false;
437
		$config['dhcpdv6'][$if]['ddnsreverse'] = ($_POST['ddnsreverse']) ? true : false;
438
		$config['dhcpdv6'][$if]['ddnsclientupdates'] = $_POST['ddnsclientupdates'];
439

    
440
		unset($config['dhcpdv6'][$if]['ntpserver']);
441
		if ($_POST['ntp1']) {
442
			$config['dhcpdv6'][$if]['ntpserver'][] = $_POST['ntp1'];
443
		}
444
		if ($_POST['ntp2']) {
445
			$config['dhcpdv6'][$if]['ntpserver'][] = $_POST['ntp2'];
446
		}
447

    
448
		$config['dhcpdv6'][$if]['tftp'] = $_POST['tftp'];
449
		$config['dhcpdv6'][$if]['ldap'] = $_POST['ldap'];
450
		$config['dhcpdv6'][$if]['netboot'] = ($_POST['netboot']) ? true : false;
451
		$config['dhcpdv6'][$if]['bootfile_url'] = $_POST['bootfile_url'];
452
		$config['dhcpdv6'][$if]['dhcpv6leaseinlocaltime'] = $_POST['dhcpv6leaseinlocaltime'];
453

    
454
		// Handle the custom options rowhelper
455
		if (isset($config['dhcpdv6'][$if]['numberoptions']['item'])) {
456
			unset($config['dhcpdv6'][$if]['numberoptions']['item']);
457
		}
458

    
459
		$config['dhcpdv6'][$if]['numberoptions'] = $numberoptions;
460

    
461
		write_config();
462

    
463
		$changes_applied = true;
464
		$retval = dhcpv6_apply_changes($dhcpdv6_enable_changed);
465
	}
466
}
467

    
468
if ($_GET['act'] == "del") {
469
	if ($a_maps[$_GET['id']]) {
470
		unset($a_maps[$_GET['id']]);
471
		write_config();
472
		if (isset($config['dhcpdv6'][$if]['enable'])) {
473
			mark_subsystem_dirty('staticmapsv6');
474
			if (isset($config['dnsmasq']['enable']) && isset($config['dnsmasq']['regdhcpstaticv6'])) {
475
				mark_subsystem_dirty('hosts');
476
			}
477
		}
478
		header("Location: services_dhcpv6.php?if={$if}");
479
		exit;
480
	}
481
}
482

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

    
485
if (!empty($if) && isset($iflist[$if])) {
486
	$pgtitle[] = $iflist[$if];
487
	$pgtitle[] = gettext("DHCPv6 Server");
488
}
489
$shortcut_section = "dhcp6";
490

    
491
include("head.inc");
492

    
493
if ($input_errors) {
494
	print_input_errors($input_errors);
495
}
496

    
497
if ($changes_applied) {
498
	print_apply_result_box($retval);
499
}
500

    
501
if (is_subsystem_dirty('staticmaps')) {
502
	print_apply_box(gettext('The static mapping configuration has been changed.') . '<br />' . gettext('The changes must be applied for them to take effect.'));
503
}
504

    
505
/* active tabs */
506
$tab_array = array();
507
$tabscounter = 0;
508
$i = 0;
509

    
510
foreach ($iflist as $ifent => $ifname) {
511
	$oc = $config['interfaces'][$ifent];
512
	$valid_if_ipaddrv6 = (bool) ($oc['ipaddrv6'] == 'track6' ||
513
	    (is_ipaddrv6($oc['ipaddrv6']) &&
514
	    !is_linklocal($oc['ipaddrv6'])));
515

    
516
	if ((!is_array($config['dhcpdv6'][$ifent]) ||
517
	    !isset($config['dhcpdv6'][$ifent]['enable'])) &&
518
	    !$valid_if_ipaddrv6) {
519
		continue;
520
	}
521

    
522
	if ($ifent == $if) {
523
		$active = true;
524
	} else {
525
		$active = false;
526
	}
527

    
528
	$tab_array[] = array($ifname, $active, "services_dhcpv6.php?if={$ifent}");
529
	$tabscounter++;
530
}
531

    
532
/* tack on PPPoE or PPtP servers here */
533
/* pppoe server */
534
if (is_array($config['pppoes']['pppoe'])) {
535
	foreach ($config['pppoes']['pppoe'] as $pppoe) {
536
		if ($pppoe['mode'] == "server") {
537
			$ifent = "poes". $pppoe['pppoeid'];
538
			$ifname = strtoupper($ifent);
539

    
540
			if ($ifent == $if) {
541
				$active = true;
542
			} else {
543
				$active = false;
544
			}
545

    
546
			$tab_array[] = array($ifname, $active, "services_dhcpv6.php?if={$ifent}");
547
			$tabscounter++;
548
		}
549
	}
550
}
551

    
552
if ($tabscounter == 0) {
553
	print_info_box(gettext("The DHCPv6 Server can only be enabled on interfaces configured with a static IPv6 address. This system has none."), 'danger');
554
	include("foot.inc");
555
	exit;
556
}
557

    
558
display_top_tabs($tab_array);
559

    
560
$tab_array = array();
561
$tab_array[] = array(gettext("DHCPv6 Server"),		 true,	"services_dhcpv6.php?if={$if}");
562
$tab_array[] = array(gettext("Router Advertisements"), false, "services_router_advertisements.php?if={$if}");
563
display_top_tabs($tab_array, false, 'nav nav-tabs');
564

    
565
$form = new Form();
566

    
567
$section = new Form_Section('DHCPv6 Options');
568

    
569
if ($dhcrelay_enabled) {
570
	$section->addInput(new Form_Checkbox(
571
		'enable',
572
		'DHCPv6 Server',
573
		gettext("DHCPv6 Relay is currently enabled. DHCPv6 Server canot be enabled while the DHCPv6 Relay is enabled on any interface."),
574
		$pconfig['enable']
575
	))->setAttribute('disabled', true);
576
} else {
577
	$section->addInput(new Form_Checkbox(
578
		'enable',
579
		'DHCPv6 Server',
580
		'Enable DHCPv6 server on interface ' . $iflist[$if],
581
		$pconfig['enable']
582
	));
583
}
584

    
585
if (is_ipaddrv6($ifcfgip)) {
586

    
587
	if ($ifcfgip == "::") {
588
		$sntext = "Prefix Delegation";
589
	} else {
590
		$sntext = gen_subnetv6($ifcfgip, $ifcfgsn);
591
	}
592
	$section->addInput(new Form_StaticText(
593
		'Subnet',
594
		$sntext
595
		));
596

    
597
	$section->addInput(new Form_StaticText(
598
		'Subnet Mask',
599
		$ifcfgsn . ' bits'
600
		));
601

    
602
	$section->addInput(new Form_StaticText(
603
		'Available Range',
604
		$range_from = gen_subnetv6($ifcfgip, $ifcfgsn) . ' to ' . gen_subnetv6_max($ifcfgip, $ifcfgsn)
605
		))->setHelp($trackifname ? 'Prefix Delegation subnet will be appended to the beginning of the defined range':'');
606
}
607

    
608
if ($is_olsr_enabled) {
609
	$section->addInput(new Form_Select(
610
	'netmask',
611
	'Subnet Mask',
612
	$pconfig['netmask'],
613
	array_combine(range(128, 1, -1), range(128, 1, -1))
614
	));
615
}
616

    
617
$f1 = new Form_Input(
618
	'range_from',
619
	null,
620
	'text',
621
	$pconfig['range_from']
622
);
623

    
624
$f1->setHelp('From');
625

    
626
$f2 = new Form_Input(
627
	'range_to',
628
	null,
629
	'text',
630
	$pconfig['range_to']
631
);
632

    
633
$f2->setHelp('To');
634

    
635
$group = new Form_Group('Range');
636

    
637
$group->add($f1);
638
$group->add($f2);
639

    
640
$section->add($group);
641

    
642
$f1 = new Form_Input(
643
	'prefixrange_from',
644
	null,
645
	'text',
646
	$pconfig['prefixrange_from']
647
);
648

    
649
$f1->setHelp('From');
650

    
651
$f2 = new Form_Input(
652
	'prefixrange_to',
653
	null,
654
	'text',
655
	$pconfig['prefixrange_to']
656
);
657

    
658
$f2->setHelp('To');
659

    
660
$group = new Form_Group('Prefix Delegation Range');
661

    
662
$group->add($f1);
663
$group->add($f2);
664

    
665
$section->add($group);
666

    
667
$section->addInput(new Form_Select(
668
	'prefixrange_length',
669
	'Prefix Delegation Size',
670
	$pconfig['prefixrange_length'],
671
	array(
672
		'48' => '48',
673
		'52' => '52',
674
		'56' => '56',
675
		'59' => '59',
676
		'60' => '60',
677
		'61' => '61',
678
		'62' => '62',
679
		'63' => '63',
680
		'64' => '64'
681
		)
682
))->setHelp('A Prefix range can be defined 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.');
683

    
684
$group = new Form_Group('DNS Servers');
685

    
686
for ($i=1;$i<=4; $i++) {
687
	$group->add(new Form_input(
688
		'dns' . $i,
689
		null,
690
		'text',
691
		$pconfig['dns' . $i],
692
		['placeholder' => 'DNS ' . $i]
693
	));
694
}
695

    
696
$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.');
697
$section->add($group);
698

    
699
$section->addInput(new Form_Input(
700
	'domain',
701
	'Domain name',
702
	'text',
703
	$pconfig['domain']
704
))->setHelp('The default is to use the domain name of this system as the default domain name provided by DHCP. An alternate domain name may be specified here. ');
705

    
706
$section->addInput(new Form_Input(
707
	'domainsearchlist',
708
	'Domain search list',
709
	'text',
710
	$pconfig['domainsearchlist']
711
))->setHelp('The DHCP server can optionally provide a domain search list. Use the semicolon character as separator.');
712

    
713
$section->addInput(new Form_Input(
714
	'deftime',
715
	'Default lease time',
716
	'text',
717
	$pconfig['deftime']
718
))->setHelp('Lease time in seconds. Used for clients that do not ask for a specific expiration time. ' . ' <br />' .
719
			'The default is 7200 seconds.');
720

    
721
$section->addInput(new Form_Input(
722
	'maxtime',
723
	'Max lease time',
724
	'text',
725
	$pconfig['maxtime']
726
))->setHelp('Maximum lease time for clients that ask for a specific expiration time.' . ' <br />' .
727
			'The default is 86400 seconds.');
728

    
729
$section->addInput(new Form_Checkbox(
730
	'dhcpv6leaseinlocaltime',
731
	'Time Format Change',
732
	'Change DHCPv6 display lease time from UTC to local time',
733
	$pconfig['dhcpv6leaseinlocaltime']
734
))->setHelp('By default DHCPv6 leases are displayed in UTC time. ' .
735
			'By checking this box DHCPv6 lease time will be displayed in local time and set to time zone selected. ' .
736
			'This will be used for all DHCPv6 interfaces lease time.');
737

    
738
$btnadv = new Form_Button(
739
	'btnadvdns',
740
	'Display Advanced',
741
	null,
742
	'fa-cog'
743
);
744

    
745
$btnadv->setAttribute('type','button')->addClass('btn-info btn-sm');
746

    
747
$section->addInput(new Form_StaticText(
748
	'Dynamic DNS',
749
	$btnadv
750
));
751

    
752
$section->addInput(new Form_Checkbox(
753
	'ddnsupdate',
754
	'DHCP Registration',
755
	'Enable registration of DHCP client names in DNS.',
756
	$pconfig['ddnsupdate']
757
));
758

    
759
$section->addInput(new Form_Input(
760
	'ddnsdomain',
761
	'DDNS Domain',
762
	'text',
763
	$pconfig['ddnsdomain']
764
))->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.');
765

    
766
$section->addInput(new Form_Checkbox(
767
	'ddnsforcehostname',
768
	'DDNS Hostnames',
769
	'Force dynamic DNS hostname to be the same as configured hostname for Static Mappings',
770
	$pconfig['ddnsforcehostname']
771
))->setHelp('Default registers host name option supplied by DHCP client.');
772

    
773
$section->addInput(new Form_IpAddress(
774
	'ddnsdomainprimary',
775
	'DDNS Server IP',
776
	$pconfig['ddnsdomainprimary'],
777
	'V4'
778
))->setHelp('Enter the primary domain name server IPv4 address for the dynamic domain name.');
779

    
780
$section->addInput(new Form_Input(
781
	'ddnsdomainkeyname',
782
	'DDNS Domain Key name',
783
	'text',
784
	$pconfig['ddnsdomainkeyname']
785
))->setHelp('Enter the dynamic DNS domain key name which will be used to register client names in the DNS server.');
786

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

    
794
$section->addInput(new Form_Select(
795
	'ddnsclientupdates',
796
	'DDNS Client Updates',
797
	$pconfig['ddnsclientupdates'],
798
	array(
799
	    'allow' => gettext('Allow'),
800
	    'deny' => gettext('Deny'),
801
	    'ignore' => gettext('Ignore'))
802
))->setHelp('How Forward entries are handled when client indicates they wish to update DNS.  ' .
803
	    'Allow prevents DHCP from updating Forward entries, Deny indicates that DHCP will ' .
804
	    'do the updates and the client should not, Ignore specifies that DHCP will do the ' .
805
	    'update and the client can also attempt the update usually using a different domain name.');
806

    
807
$section->addInput(new Form_Checkbox(
808
	'ddnsreverse',
809
	'DDNS Reverse',
810
	'Add reverse dynamic DNS entries.',
811
	$pconfig['ddnsreverse']
812
));
813

    
814
$btnadv = new Form_Button(
815
	'btnadvntp',
816
	'Display Advanced',
817
	null,
818
	'fa-cog'
819
);
820

    
821
$btnadv->setAttribute('type','button')->addClass('btn-info btn-sm');
822

    
823
$section->addInput(new Form_StaticText(
824
	'NTP servers',
825
	$btnadv
826
));
827

    
828
$group = new Form_Group('NTP Servers');
829

    
830
$group->add(new Form_Input(
831
	'ntp1',
832
	'NTP Server 1',
833
	'text',
834
	$pconfig['ntp1'],
835
	['placeholder' => 'NTP 1']
836
));
837

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

    
846
$group->addClass('ntpclass');
847

    
848
$section->add($group);
849

    
850
$btnadv = new Form_Button(
851
	'btnadvldap',
852
	'Display Advanced',
853
	null,
854
	'fa-cog'
855
);
856

    
857
$btnadv->setAttribute('type','button')->addClass('btn-info btn-sm');
858

    
859
$section->addInput(new Form_StaticText(
860
	'LDAP',
861
	$btnadv
862
));
863

    
864
$section->addInput(new Form_Input(
865
	'ldap',
866
	'LDAP URI',
867
	'text',
868
	$pconfig['ldap']
869
));
870

    
871
$btnadv = new Form_Button(
872
	'btnadvnetboot',
873
	'Display Advanced',
874
	null,
875
	'fa-cog'
876
);
877

    
878
$btnadv->setAttribute('type','button')->addClass('btn-info btn-sm');
879

    
880
$section->addInput(new Form_StaticText(
881
	'Network booting',
882
	$btnadv
883
));
884

    
885
$section->addInput(new Form_Checkbox(
886
	'shownetboot',
887
	'Network booting',
888
	'Enable Network Booting',
889
	$pconfig['shownetboot']
890
));
891

    
892
$section->addInput(new Form_Input(
893
	'bootfile_url',
894
	'Bootfile URL',
895
	'text',
896
	$pconfig['bootfile_url']
897
));
898

    
899
$btnadv = new Form_Button(
900
	'btnadvopts',
901
	'Display Advanced',
902
	null,
903
	'fa-cog'
904
);
905

    
906
$btnadv->setAttribute('type','button')->addClass('btn-info btn-sm');
907

    
908
$section->addInput(new Form_StaticText(
909
	'Additional BOOTP/DHCP Options',
910
	$btnadv
911
));
912

    
913
$form->add($section);
914

    
915
$title = 'Show Additional BOOTP/DHCP Options';
916

    
917
if (!$pconfig['numberoptions']) {
918
	$noopts = true;
919
	$pconfig['numberoptions']['item'] = array(0 => array('number' => "", 'value' => ""));
920
} else {
921
	$noopts = false;
922
}
923

    
924
$counter = 0;
925
$last = count($pconfig['numberoptions']['item']) - 1;
926

    
927
foreach ($pconfig['numberoptions']['item'] as $item) {
928
	$group = new Form_Group(null);
929
	$group->addClass('repeatable');
930
	$group->addClass('adnloptions');
931

    
932
	$group->add(new Form_Input(
933
		'number' . $counter,
934
		null,
935
		'text',
936
		$item['number']
937
	))->setHelp($counter == $last ? 'Number':null);
938

    
939
	$group->add(new Form_Input(
940
		'value' . $counter,
941
		null,
942
		'text',
943
		base64_decode($item['value'])
944
	))->setHelp($counter == $last ? 'Value':null);
945

    
946
	$btn = new Form_Button(
947
		'deleterow' . $counter,
948
		'Delete',
949
		null,
950
		'fa-trash'
951
	);
952

    
953
	$btn->addClass('btn-warning');
954
	$group->add($btn);
955
	$section->add($group);
956
	$counter++;
957
}
958

    
959

    
960
$btnaddopt = new Form_Button(
961
	'addrow',
962
	'Add Option',
963
	null,
964
	'fa-plus'
965
);
966

    
967
$btnaddopt->removeClass('btn-primary')->addClass('btn-success btn-sm');
968

    
969
$section->addInput($btnaddopt);
970

    
971
$section->addInput(new Form_Input(
972
	'if',
973
	null,
974
	'hidden',
975
	$if
976
));
977

    
978
print($form);
979

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

    
1047
<nav class="action-buttons">
1048
	<a href="services_dhcpv6_edit.php?if=<?=$if?>" class="btn btn-sm btn-success"/>
1049
		<i class="fa fa-plus icon-embed-btn"></i>
1050
		<?=gettext("Add")?>
1051
	</a>
1052
</nav>
1053

    
1054
<script type="text/javascript">
1055
//<![CDATA[
1056
events.push(function() {
1057

    
1058
	// Show advanced DNS options ======================================================================================
1059
	var showadvdns = false;
1060

    
1061
	function show_advdns(ispageload) {
1062
		var text;
1063
		// On page load decide the initial state based on the data.
1064
		if (ispageload) {
1065
<?php
1066
			if (!$pconfig['ddnsupdate'] &&
1067
			    !$pconfig['ddnsforcehostname'] &&
1068
			    empty($pconfig['ddnsdomain']) &&
1069
			    empty($pconfig['ddnsdomainprimary']) &&
1070
			    empty($pconfig['ddnsdomainkeyname']) &&
1071
			    empty($pconfig['ddnsdomainkey']) &&
1072
			    (empty($pconfig['ddnsclientupdates']) || ($pconfig['ddnsclientupdates'] == "allow")) &&
1073
			    !$pconfig['ddnsreverse']) {
1074
				$showadv = false;
1075
			} else {
1076
				$showadv = true;
1077
			}
1078
?>
1079
			showadvdns = <?php if ($showadv) {echo 'true';} else {echo 'false';} ?>;
1080
		} else {
1081
			// It was a click, swap the state.
1082
			showadvdns = !showadvdns;
1083
		}
1084

    
1085
		hideCheckbox('ddnsupdate', !showadvdns);
1086
		hideInput('ddnsdomain', !showadvdns);
1087
		hideCheckbox('ddnsforcehostname', !showadvdns);
1088
		hideInput('ddnsdomainprimary', !showadvdns);
1089
		hideInput('ddnsdomainkeyname', !showadvdns);
1090
		hideInput('ddnsdomainkey', !showadvdns);
1091
		hideInput('ddnsclientupdates', !showadvdns);
1092
		hideCheckbox('ddnsreverse', !showadvdns);
1093

    
1094
		if (showadvdns) {
1095
			text = "<?=gettext('Hide Advanced');?>";
1096
		} else {
1097
			text = "<?=gettext('Display Advanced');?>";
1098
		}
1099
		$('#btnadvdns').html('<i class="fa fa-cog"></i> ' + text);
1100
	}
1101

    
1102
	$('#btnadvdns').click(function(event) {
1103
		show_advdns();
1104
	});
1105

    
1106
	// Show advanced NTP options ======================================================================================
1107
	var showadvntp = false;
1108

    
1109
	function show_advntp(ispageload) {
1110
		var text;
1111
		// On page load decide the initial state based on the data.
1112
		if (ispageload) {
1113
<?php
1114
			if (empty($pconfig['ntp1']) && empty($pconfig['ntp2'])) {
1115
				$showadv = false;
1116
			} else {
1117
				$showadv = true;
1118
			}
1119
?>
1120
			showadvntp = <?php if ($showadv) {echo 'true';} else {echo 'false';} ?>;
1121
		} else {
1122
			// It was a click, swap the state.
1123
			showadvntp = !showadvntp;
1124
		}
1125

    
1126
		hideInput('ntp1', !showadvntp);
1127
		hideInput('ntp2', !showadvntp);
1128

    
1129
		if (showadvntp) {
1130
			text = "<?=gettext('Hide Advanced');?>";
1131
		} else {
1132
			text = "<?=gettext('Display Advanced');?>";
1133
		}
1134
		$('#btnadvntp').html('<i class="fa fa-cog"></i> ' + text);
1135
	}
1136

    
1137
	$('#btnadvntp').click(function(event) {
1138
		show_advntp();
1139
	});
1140

    
1141
	// Show advanced LDAP options ======================================================================================
1142
	var showadvldap = false;
1143

    
1144
	function show_advldap(ispageload) {
1145
		var text;
1146
		// On page load decide the initial state based on the data.
1147
		if (ispageload) {
1148
<?php
1149
			if (empty($pconfig['ldap'])) {
1150
				$showadv = false;
1151
			} else {
1152
				$showadv = true;
1153
			}
1154
?>
1155
			showadvldap = <?php if ($showadv) {echo 'true';} else {echo 'false';} ?>;
1156
		} else {
1157
			// It was a click, swap the state.
1158
			showadvldap = !showadvldap;
1159
		}
1160

    
1161
		hideInput('ldap', !showadvldap);
1162

    
1163
		if (showadvldap) {
1164
			text = "<?=gettext('Hide Advanced');?>";
1165
		} else {
1166
			text = "<?=gettext('Display Advanced');?>";
1167
		}
1168
		$('#btnadvldap').html('<i class="fa fa-cog"></i> ' + text);
1169
	}
1170

    
1171
	$('#btnadvldap').click(function(event) {
1172
		show_advldap();
1173
	});
1174

    
1175
	// Show advanced Netboot options ======================================================================================
1176
	var showadvnetboot = false;
1177

    
1178
	function show_advnetboot(ispageload) {
1179
		var text;
1180
		// On page load decide the initial state based on the data.
1181
		if (ispageload) {
1182
<?php
1183
			if (!$pconfig['shownetboot'] && empty($pconfig['bootfile_url'])) {
1184
				$showadv = false;
1185
			} else {
1186
				$showadv = true;
1187
			}
1188
?>
1189
			showadvnetboot = <?php if ($showadv) {echo 'true';} else {echo 'false';} ?>;
1190
		} else {
1191
			// It was a click, swap the state.
1192
			showadvnetboot = !showadvnetboot;
1193
		}
1194

    
1195
		hideCheckbox('shownetboot', !showadvnetboot);
1196
		hideInput('bootfile_url', !showadvnetboot);
1197

    
1198
		if (showadvnetboot) {
1199
			text = "<?=gettext('Hide Advanced');?>";
1200
		} else {
1201
			text = "<?=gettext('Display Advanced');?>";
1202
		}
1203
		$('#btnadvnetboot').html('<i class="fa fa-cog"></i> ' + text);
1204
	}
1205

    
1206
	$('#btnadvnetboot').click(function(event) {
1207
		show_advnetboot();
1208
	});
1209

    
1210
	// Show advanced additional opts options ===========================================================================
1211
	var showadvopts = false;
1212

    
1213
	function show_advopts(ispageload) {
1214
		var text;
1215
		// On page load decide the initial state based on the data.
1216
		if (ispageload) {
1217
<?php
1218
			if (empty($pconfig['numberoptions']) ||
1219
			    (empty($pconfig['numberoptions']['item'][0]['number']) && (empty($pconfig['numberoptions']['item'][0]['value'])))) {
1220
				$showadv = false;
1221
			} else {
1222
				$showadv = true;
1223
			}
1224
?>
1225
			showadvopts = <?php if ($showadv) {echo 'true';} else {echo 'false';} ?>;
1226
		} else {
1227
			// It was a click, swap the state.
1228
			showadvopts = !showadvopts;
1229
		}
1230

    
1231
		hideClass('adnloptions', !showadvopts);
1232
		hideInput('addrow', !showadvopts);
1233

    
1234
		if (showadvopts) {
1235
			text = "<?=gettext('Hide Advanced');?>";
1236
		} else {
1237
			text = "<?=gettext('Display Advanced');?>";
1238
		}
1239
		$('#btnadvopts').html('<i class="fa fa-cog"></i> ' + text);
1240
	}
1241

    
1242
	$('#btnadvopts').click(function(event) {
1243
		show_advopts();
1244
		checkLastRow();
1245
	});
1246

    
1247
	// On initial load
1248
	show_advdns(true);
1249
	show_advntp(true);
1250
	show_advldap(true);
1251
	show_advnetboot(true);
1252
	show_advopts(true);
1253
	if ($('#enable').prop('checked')) {
1254
		hideClass('adnloptions', <?php echo json_encode($noopts); ?>);
1255
		hideInput('addrow', <?php echo json_encode($noopts); ?>);
1256
	} else {
1257
		hideClass('adnloptions', true);
1258
		hideInput('addrow', true);
1259
	}
1260

    
1261
});
1262
//]]>
1263
</script>
1264

    
1265
<?php include('foot.inc');
(120-120/225)