Project

General

Profile

Download (66.6 KB) Statistics
| Branch: | Tag: | Revision:
1
<?php
2
/*
3
	system.inc
4

    
5
	part of pfSense (https://www.pfsense.org)
6
	Copyright (c) 2004-2016 Electric Sheep Fencing, LLC.
7
	All rights reserved.
8

    
9
	originally part of m0n0wall (http://m0n0.ch/wall)
10
	Copyright (C) 2003-2004 Manuel Kasper <mk@neon1.net>.
11
	All rights reserved.
12

    
13
	Redistribution and use in source and binary forms, with or without
14
	modification, are permitted provided that the following conditions are met:
15

    
16
	1. Redistributions of source code must retain the above copyright notice,
17
	   this list of conditions and the following disclaimer.
18

    
19
	2. Redistributions in binary form must reproduce the above copyright
20
	   notice, this list of conditions and the following disclaimer in
21
	   the documentation and/or other materials provided with the
22
	   distribution.
23

    
24
	3. All advertising materials mentioning features or use of this software
25
	   must display the following acknowledgment:
26
	   "This product includes software developed by the pfSense Project
27
	   for use in the pfSense® software distribution. (http://www.pfsense.org/).
28

    
29
	4. The names "pfSense" and "pfSense Project" must not be used to
30
	   endorse or promote products derived from this software without
31
	   prior written permission. For written permission, please contact
32
	   coreteam@pfsense.org.
33

    
34
	5. Products derived from this software may not be called "pfSense"
35
	   nor may "pfSense" appear in their names without prior written
36
	   permission of the Electric Sheep Fencing, LLC.
37

    
38
	6. Redistributions of any form whatsoever must retain the following
39
	   acknowledgment:
40

    
41
	"This product includes software developed by the pfSense Project
42
	for use in the pfSense software distribution (http://www.pfsense.org/).
43

    
44
	THIS SOFTWARE IS PROVIDED BY THE pfSense PROJECT ``AS IS'' AND ANY
45
	EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
46
	IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
47
	PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE pfSense PROJECT OR
48
	ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
49
	SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
50
	NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
51
	LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
52
	HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
53
	STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
54
	ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
55
	OF THE POSSIBILITY OF SUCH DAMAGE.
56
*/
57

    
58
function activate_powerd() {
59
	global $config, $g;
60

    
61
	if (is_process_running("powerd")) {
62
		exec("/usr/bin/killall powerd");
63
	}
64
	if (isset($config['system']['powerd_enable'])) {
65
		if ($g["platform"] == "nanobsd") {
66
			exec("/sbin/kldload cpufreq");
67
		}
68

    
69
		$ac_mode = "hadp";
70
		if (!empty($config['system']['powerd_ac_mode'])) {
71
			$ac_mode = $config['system']['powerd_ac_mode'];
72
		}
73

    
74
		$battery_mode = "hadp";
75
		if (!empty($config['system']['powerd_battery_mode'])) {
76
			$battery_mode = $config['system']['powerd_battery_mode'];
77
		}
78

    
79
		$normal_mode = "hadp";
80
		if (!empty($config['system']['powerd_normal_mode'])) {
81
			$normal_mode = $config['system']['powerd_normal_mode'];
82
		}
83

    
84
		mwexec("/usr/sbin/powerd -b $battery_mode -a $ac_mode -n $normal_mode");
85
	}
86
}
87

    
88
function get_default_sysctl_value($id) {
89
	global $sysctls;
90

    
91
	if (isset($sysctls[$id])) {
92
		return $sysctls[$id];
93
	}
94
}
95

    
96
function get_sysctl_descr($sysctl) {
97
	unset($output);
98
	$_gb = exec("/sbin/sysctl -nd {$sysctl}", $output);
99

    
100
	return $output[0];
101
}
102

    
103
function system_get_sysctls() {
104
	global $config, $sysctls;
105

    
106
	$disp_sysctl = array();
107
	$disp_cache = array();
108
	if (is_array($config['sysctl']) && is_array($config['sysctl']['item'])) {
109
		foreach ($config['sysctl']['item'] as $id => $tunable) {
110
			if ($tunable['value'] == "default") {
111
				$value = get_default_sysctl_value($tunable['tunable']);
112
			} else {
113
				$value = $tunable['value'];
114
			}
115

    
116
			$disp_sysctl[$id] = $tunable;
117
			$disp_sysctl[$id]['modified'] = true;
118
			$disp_cache[$tunable['tunable']] = 'set';
119
		}
120
	}
121

    
122
	foreach ($sysctls as $sysctl => $value) {
123
		if (isset($disp_cache[$sysctl])) {
124
			continue;
125
		}
126

    
127
		$disp_sysctl[$sysctl] = array('tunable' => $sysctl, 'value' => $value, 'descr' => get_sysctl_descr($sysctl));
128
	}
129
	unset($disp_cache);
130
	return $disp_sysctl;
131
}
132

    
133
function activate_sysctls() {
134
	global $config, $g, $sysctls;
135

    
136
	if (is_array($config['sysctl']) && is_array($config['sysctl']['item'])) {
137
		foreach ($config['sysctl']['item'] as $tunable) {
138
			if ($tunable['value'] == "default") {
139
				$value = get_default_sysctl_value($tunable['tunable']);
140
			} else {
141
				$value = $tunable['value'];
142
			}
143

    
144
			$sysctls[$tunable['tunable']] = $value;
145
		}
146
	}
147

    
148
	set_sysctl($sysctls);
149
}
150

    
151
function system_resolvconf_generate($dynupdate = false) {
152
	global $config, $g;
153

    
154
	if (isset($config['system']['developerspew'])) {
155
		$mt = microtime();
156
		echo "system_resolvconf_generate() being called $mt\n";
157
	}
158

    
159
	$syscfg = $config['system'];
160

    
161
	if ((((isset($config['dnsmasq']['enable'])) &&
162
	      (empty($config['dnsmasq']['port']) || $config['dnsmasq']['port'] == "53") &&
163
	      (empty($config['dnsmasq']['interface']) ||
164
	       in_array("lo0", explode(",", $config['dnsmasq']['interface'])))) ||
165
	     ((isset($config['unbound']['enable'])) &&
166
	      (empty($config['unbound']['port']) || $config['unbound']['port'] == "53") &&
167
	      (empty($config['unbound']['active_interface']) ||
168
	       in_array("lo0", explode(",", $config['unbound']['active_interface'])) ||
169
	       in_array("all", explode(",", $config['unbound']['active_interface']), true)))) &&
170
	     (!isset($config['system']['dnslocalhost']))) {
171
		$resolvconf .= "nameserver 127.0.0.1\n";
172
	}
173

    
174
	if (isset($syscfg['dnsallowoverride'])) {
175
		/* get dynamically assigned DNS servers (if any) */
176
		$ns = array_unique(get_searchdomains());
177
		foreach ($ns as $searchserver) {
178
			if ($searchserver) {
179
				$resolvconf .= "search {$searchserver}\n";
180
			}
181
		}
182
		$ns = array_unique(get_nameservers());
183
		foreach ($ns as $nameserver) {
184
			if ($nameserver) {
185
				$resolvconf .= "nameserver $nameserver\n";
186
			}
187
		}
188
	} else {
189
		$ns = array();
190
		// Do not create blank search/domain lines, it can break tools like dig.
191
		if ($syscfg['domain']) {
192
			$resolvconf .= "search {$syscfg['domain']}\n";
193
		}
194
	}
195
	if (is_array($syscfg['dnsserver'])) {
196
		foreach ($syscfg['dnsserver'] as $sys_dnsserver) {
197
			if ($sys_dnsserver && (!in_array($sys_dnsserver, $ns))) {
198
				$resolvconf .= "nameserver $sys_dnsserver\n";
199
			}
200
		}
201
	}
202

    
203
	// Add EDNS support
204
	if (isset($config['unbound']['enable']) && isset($config['unbound']['edns'])) {
205
		$resolvconf .= "options edns0\n";
206
	}
207

    
208
	$dnslock = lock('resolvconf', LOCK_EX);
209

    
210
	$fd = fopen("{$g['varetc_path']}/resolv.conf", "w");
211
	if (!$fd) {
212
		printf("Error: cannot open resolv.conf in system_resolvconf_generate().\n");
213
		unlock($dnslock);
214
		return 1;
215
	}
216

    
217
	fwrite($fd, $resolvconf);
218
	fclose($fd);
219

    
220
	// Prevent resolvconf(8) from rewriting our resolv.conf
221
	$fd = fopen("{$g['varetc_path']}/resolvconf.conf", "w");
222
	if (!$fd) {
223
		printf("Error: cannot open resolvconf.conf in system_resolvconf_generate().\n");
224
		return 1;
225
	}
226
	fwrite($fd, "resolv_conf=\"/dev/null\"\n");
227
	fclose($fd);
228

    
229
	if (!platform_booting()) {
230
		/* restart dhcpd (nameservers may have changed) */
231
		if (!$dynupdate) {
232
			services_dhcpd_configure();
233
		}
234
	}
235

    
236
	/* setup static routes for DNS servers. */
237
	for ($dnscounter=1; $dnscounter<5; $dnscounter++) {
238
		/* setup static routes for dns servers */
239
		$dnsgw = "dns{$dnscounter}gw";
240
		if (isset($config['system'][$dnsgw])) {
241
			if (empty($config['system'][$dnsgw]) ||
242
			    $config['system'][$dnsgw] == "none") {
243
				continue;
244
			}
245
			$gwname = $config['system'][$dnsgw];
246
			$gatewayip = lookup_gateway_ip_by_name($gwname);
247
			$inet6 = is_ipaddrv6($gatewayip) ? '-inet6 ' : '';
248
			/* dns server array starts at 0 */
249
			$dnsserver = $syscfg['dnsserver'][$dnscounter - 1];
250

    
251
			if (is_ipaddr($gatewayip)) {
252
				$cmd = 'change';
253
			} else {
254
				/* Remove old route when disable gw */
255
				$cmd = 'delete';
256
				$gatewayip = '';
257
			}
258

    
259
			mwexec("/sbin/route {$cmd} -host {$inet6}{$dnsserver} {$gatewayip}");
260
			if (isset($config['system']['route-debug'])) {
261
				$mt = microtime();
262
				log_error("ROUTING debug: $mt - route {$cmd} -host {$inet6}{$dnsserver} {$gatewayip}");
263
			}
264
		}
265
	}
266

    
267
	unlock($dnslock);
268

    
269
	return 0;
270
}
271

    
272
function get_searchdomains() {
273
	global $config, $g;
274

    
275
	$master_list = array();
276

    
277
	// Read in dhclient nameservers
278
	$search_list = glob("/var/etc/searchdomain_*");
279
	if (is_array($search_list)) {
280
		foreach ($search_list as $fdns) {
281
			$contents = file($fdns, FILE_IGNORE_NEW_LINES | FILE_SKIP_EMPTY_LINES);
282
			if (!is_array($contents)) {
283
				continue;
284
			}
285
			foreach ($contents as $dns) {
286
				if (is_hostname($dns)) {
287
					$master_list[] = $dns;
288
				}
289
			}
290
		}
291
	}
292

    
293
	return $master_list;
294
}
295

    
296
function get_nameservers() {
297
	global $config, $g;
298
	$master_list = array();
299

    
300
	// Read in dhclient nameservers
301
	$dns_lists = glob("/var/etc/nameserver_*");
302
	if (is_array($dns_lists)) {
303
		foreach ($dns_lists as $fdns) {
304
			$contents = file($fdns, FILE_IGNORE_NEW_LINES | FILE_SKIP_EMPTY_LINES);
305
			if (!is_array($contents)) {
306
				continue;
307
			}
308
			foreach ($contents as $dns) {
309
				if (is_ipaddr($dns)) {
310
					$master_list[] = $dns;
311
				}
312
			}
313
		}
314
	}
315

    
316
	// Read in any extra nameservers
317
	if (file_exists("/var/etc/nameservers.conf")) {
318
		$dns_s = file("/var/etc/nameservers.conf", FILE_IGNORE_NEW_LINES | FILE_SKIP_EMPTY_LINES);
319
		if (is_array($dns_s)) {
320
			foreach ($dns_s as $dns) {
321
				if (is_ipaddr($dns)) {
322
					$master_list[] = $dns;
323
				}
324
			}
325
		}
326
	}
327

    
328
	return $master_list;
329
}
330

    
331
function system_hosts_generate() {
332
	global $config, $g;
333
	if (isset($config['system']['developerspew'])) {
334
		$mt = microtime();
335
		echo "system_hosts_generate() being called $mt\n";
336
	}
337

    
338
	$syscfg = $config['system'];
339
	// prefer dnsmasq for hosts generation where it's enabled. It relies
340
	// on hosts for name resolution of its overrides, unbound does not.
341
	if (isset($config['dnsmasq']) && isset($config['dnsmasq']['enable'])) {
342
		$dnsmasqcfg = $config['dnsmasq'];
343
	} else {
344
		$dnsmasqcfg = $config['unbound'];
345
	}
346

    
347
	$hosts = "127.0.0.1	localhost localhost.{$syscfg['domain']}\n";
348
	$hosts .= "::1		localhost localhost.{$syscfg['domain']}\n";
349
	$lhosts = "";
350
	$dhosts = "";
351

    
352
	if ($config['interfaces']['lan']) {
353
		$cfgip = get_interface_ip("lan");
354
		if (is_ipaddr($cfgip)) {
355
			$hosts .= "{$cfgip}	{$syscfg['hostname']}.{$syscfg['domain']} {$syscfg['hostname']}\n";
356
		}
357
		$cfgipv6 = get_interface_ipv6("lan");
358
		if (is_ipaddrv6($cfgipv6)) {
359
			$hosts .= "{$cfgipv6}	{$syscfg['hostname']}.{$syscfg['domain']} {$syscfg['hostname']}\n";
360
		}
361
	} else {
362
		$sysiflist = get_configured_interface_list();
363
		$hosts_if_found = false;
364
		foreach ($sysiflist as $sysif) {
365
			if (!interface_has_gateway($sysif)) {
366
				$cfgip = get_interface_ip($sysif);
367
				if (is_ipaddr($cfgip)) {
368
					$hosts .= "{$cfgip}	{$syscfg['hostname']}.{$syscfg['domain']} {$syscfg['hostname']}\n";
369
					$hosts_if_found = true;
370
				}
371
				$cfgipv6 = get_interface_ipv6($sysif);
372
				if (is_ipaddrv6($cfgipv6)) {
373
					$hosts .= "{$cfgipv6}	{$syscfg['hostname']}.{$syscfg['domain']} {$syscfg['hostname']}\n";
374
					$hosts_if_found = true;
375
				}
376
				if ($hosts_if_found == true) {
377
					break;
378
				}
379
			}
380
		}
381
	}
382

    
383
	if (isset($dnsmasqcfg['enable'])) {
384
		if (!is_array($dnsmasqcfg['hosts'])) {
385
			$dnsmasqcfg['hosts'] = array();
386
		}
387

    
388
		foreach ($dnsmasqcfg['hosts'] as $host) {
389
			if ($host['host'] || $host['host'] == "0") {
390
				$lhosts .= "{$host['ip']}	{$host['host']}.{$host['domain']} {$host['host']}\n";
391
			} else {
392
				$lhosts .= "{$host['ip']}	{$host['domain']}\n";
393
			}
394
			if (!is_array($host['aliases']) || !is_array($host['aliases']['item'])) {
395
				continue;
396
			}
397
			foreach ($host['aliases']['item'] as $alias) {
398
				if ($alias['host'] || $alias['host'] == "0") {
399
					$lhosts .= "{$host['ip']}	{$alias['host']}.{$alias['domain']} {$alias['host']}\n";
400
				} else {
401
					$lhosts .= "{$host['ip']}	{$alias['domain']}\n";
402
				}
403
			}
404
		}
405
		if (isset($dnsmasqcfg['regdhcpstatic']) && is_array($config['dhcpd'])) {
406
			foreach ($config['dhcpd'] as $dhcpif => $dhcpifconf) {
407
				if (is_array($dhcpifconf['staticmap']) && isset($dhcpifconf['enable'])) {
408
					foreach ($dhcpifconf['staticmap'] as $host) {
409
						if ($host['ipaddr'] && $host['hostname'] && $host['domain']) {
410
							$dhosts .= "{$host['ipaddr']}	{$host['hostname']}.{$host['domain']} {$host['hostname']}\n";
411
						} else if ($host['ipaddr'] && $host['hostname'] && $dhcpifconf['domain']) {
412
							$dhosts .= "{$host['ipaddr']}	{$host['hostname']}.{$dhcpifconf['domain']} {$host['hostname']}\n";
413
						} else if ($host['ipaddr'] && $host['hostname']) {
414
							$dhosts .= "{$host['ipaddr']}	{$host['hostname']}.{$syscfg['domain']} {$host['hostname']}\n";
415
						}
416
					}
417
				}
418
			}
419
		}
420
		if (isset($dnsmasqcfg['regdhcpstatic']) && is_array($config['dhcpdv6'])) {
421
			foreach ($config['dhcpdv6'] as $dhcpif => $dhcpifconf) {
422
				if (is_array($dhcpifconf['staticmap']) && isset($dhcpifconf['enable'])) {
423
					$isdelegated = $config['interfaces'][$dhcpif]['ipaddrv6'] == 'track6';
424
					foreach ($dhcpifconf['staticmap'] as $host) {
425
						$ipaddrv6 = $host['ipaddrv6'];
426
						if ($ipaddrv6 && $host['hostname']) {
427
							if ($isdelegated) {
428
								$trackifname = $config['interfaces'][$dhcpif]['track6-interface'];
429
								$trackcfg = $config['interfaces'][$trackifname];
430
								$pdlen = 64 - $trackcfg['dhcp6-ia-pd-len'];
431
								$ipaddrv6 = merge_ipv6_delegated_prefix(get_interface_ipv6($dhcpif), $ipaddrv6, $pdlen);
432
							}
433
							if ($host['domain']) {
434
								$dhosts .= "{$ipaddrv6}	{$host['hostname']}.{$host['domain']} {$host['hostname']}\n";
435
							} else if ($dhcpifconf['domain']) {
436
								$dhosts .= "{$ipaddrv6}	{$host['hostname']}.{$dhcpifconf['domain']} {$host['hostname']}\n";
437
							} else {
438
								$dhosts .= "{$ipaddrv6}	{$host['hostname']}.{$syscfg['domain']} {$host['hostname']}\n";
439
							}
440
						}
441
					}
442
				}
443
			}
444
		}
445

    
446
		if (isset($dnsmasqcfg['dhcpfirst'])) {
447
			$hosts .= $dhosts . $lhosts;
448
		} else {
449
			$hosts .= $lhosts . $dhosts;
450
		}
451
	}
452

    
453
	/*
454
	 * Do not remove this because dhcpleases monitors with kqueue it needs to be
455
	 * killed before writing to hosts files.
456
	 */
457
	if (file_exists("{$g['varrun_path']}/dhcpleases.pid")) {
458
		sigkillbypid("{$g['varrun_path']}/dhcpleases.pid", "TERM");
459
		@unlink("{$g['varrun_path']}/dhcpleases.pid");
460
	}
461
	$fd = fopen("{$g['varetc_path']}/hosts", "w");
462
	if (!$fd) {
463
		log_error(gettext("Error: cannot open hosts file in system_hosts_generate()."));
464
		return 1;
465
	}
466
	fwrite($fd, $hosts);
467
	fclose($fd);
468

    
469
	if (isset($config['unbound']['enable'])) {
470
		require_once("unbound.inc");
471
		unbound_hosts_generate();
472
	}
473

    
474
	return 0;
475
}
476

    
477
function system_dhcpleases_configure() {
478
	global $config, $g;
479

    
480
	/* Start the monitoring process for dynamic dhcpclients. */
481
	if ((isset($config['dnsmasq']['enable']) && isset($config['dnsmasq']['regdhcp'])) ||
482
	    (isset($config['unbound']['enable']) && isset($config['unbound']['regdhcp']))) {
483
		/* Make sure we do not error out */
484
		mwexec("/bin/mkdir -p {$g['dhcpd_chroot_path']}/var/db");
485
		if (!file_exists("{$g['dhcpd_chroot_path']}/var/db/dhcpd.leases")) {
486
			@touch("{$g['dhcpd_chroot_path']}/var/db/dhcpd.leases");
487
		}
488

    
489
		if (isset($config['unbound']['enable'])) {
490
			$dns_pid = "unbound.pid";
491
			$unbound_conf = "-u {$g['unbound_chroot_path']}/dhcpleases_entries.conf";
492
		} else {
493
			$dns_pid = "dnsmasq.pid";
494
			$unbound_conf = "";
495
		}
496

    
497
		$pidfile = "{$g['varrun_path']}/dhcpleases.pid";
498
		if (isvalidpid($pidfile)) {
499
			/* Make sure dhcpleases is using correct unbound or dnsmasq */
500
			$_gb = exec("/bin/pgrep -F {$pidfile} -f {$dns_pid}", $output, $retval);
501
			if (intval($retval) == 0) {
502
				sigkillbypid($pidfile, "HUP");
503
				return;
504
			} else {
505
				sigkillbypid($pidfile, "TERM");
506
			}
507
		}
508

    
509
		/* To ensure we do not start multiple instances of dhcpleases, perform some clean-up first. */
510
		if (is_process_running("dhcpleases")) {
511
			sigkillbyname('dhcpleases', "TERM");
512
		}
513
		@unlink($pidfile);
514
		mwexec("/usr/local/sbin/dhcpleases -l {$g['dhcpd_chroot_path']}/var/db/dhcpd.leases -d {$config['system']['domain']} -p {$g['varrun_path']}/{$dns_pid} {$unbound_conf} -h {$g['varetc_path']}/hosts");
515
	} else {
516
		sigkillbypid($pidfile, "TERM");
517
		@unlink($pidfile);
518
	}
519
}
520

    
521
function system_hostname_configure() {
522
	global $config, $g;
523
	if (isset($config['system']['developerspew'])) {
524
		$mt = microtime();
525
		echo "system_hostname_configure() being called $mt\n";
526
	}
527

    
528
	$syscfg = $config['system'];
529

    
530
	/* set hostname */
531
	$status = mwexec("/bin/hostname " .
532
		escapeshellarg("{$syscfg['hostname']}.{$syscfg['domain']}"));
533

    
534
	/* Setup host GUID ID.  This is used by ZFS. */
535
	mwexec("/etc/rc.d/hostid start");
536

    
537
	return $status;
538
}
539

    
540
function system_routing_configure($interface = "") {
541
	global $config, $g;
542

    
543
	if (isset($config['system']['developerspew'])) {
544
		$mt = microtime();
545
		echo "system_routing_configure() being called $mt\n";
546
	}
547

    
548
	$gatewayip = "";
549
	$interfacegw = "";
550
	$gatewayipv6 = "";
551
	$interfacegwv6 = "";
552
	$foundgw = false;
553
	$foundgwv6 = false;
554
	/* tack on all the hard defined gateways as well */
555
	if (is_array($config['gateways']['gateway_item'])) {
556
		array_map('unlink', glob("{$g['tmp_path']}/*_defaultgw{,v6}", GLOB_BRACE));
557
		foreach	($config['gateways']['gateway_item'] as $gateway) {
558
			if (isset($gateway['defaultgw'])) {
559
				if ($foundgw == false && ($gateway['ipprotocol'] != "inet6" && (is_ipaddrv4($gateway['gateway']) || $gateway['gateway'] == "dynamic"))) {
560
					if (strpos($gateway['gateway'], ":")) {
561
						continue;
562
					}
563
					if ($gateway['gateway'] == "dynamic") {
564
						$gateway['gateway'] = get_interface_gateway($gateway['interface']);
565
					}
566
					$gatewayip = $gateway['gateway'];
567
					$interfacegw = $gateway['interface'];
568
					if (!empty($gateway['interface'])) {
569
						$defaultif = get_real_interface($gateway['interface']);
570
						if ($defaultif) {
571
							@file_put_contents("{$g['tmp_path']}/{$defaultif}_defaultgw", $gateway['gateway']);
572
						}
573
					}
574
					$foundgw = true;
575
				} else if ($foundgwv6 == false && ($gateway['ipprotocol'] == "inet6" && (is_ipaddrv6($gateway['gateway']) || $gateway['gateway'] == "dynamic"))) {
576
					if ($gateway['gateway'] == "dynamic") {
577
						$gateway['gateway'] = get_interface_gateway_v6($gateway['interface']);
578
					}
579
					$gatewayipv6 = $gateway['gateway'];
580
					$interfacegwv6 = $gateway['interface'];
581
					if (!empty($gateway['interface'])) {
582
						$defaultifv6 = get_real_interface($gateway['interface']);
583
						if ($defaultifv6) {
584
							@file_put_contents("{$g['tmp_path']}/{$defaultifv6}_defaultgwv6", $gateway['gateway']);
585
						}
586
					}
587
					$foundgwv6 = true;
588
				}
589
			}
590
			if ($foundgw === true && $foundgwv6 === true) {
591
				break;
592
			}
593
		}
594
	}
595
	if ($foundgw == false) {
596
		$defaultif = get_real_interface("wan");
597
		$interfacegw = "wan";
598
		$gatewayip = get_interface_gateway("wan");
599
		@file_put_contents("{$g['tmp_path']}/{$defaultif}_defaultgw", $gatewayip);
600
	}
601
	if ($foundgwv6 == false) {
602
		$defaultifv6 = get_real_interface("wan");
603
		$interfacegwv6 = "wan";
604
		$gatewayipv6 = get_interface_gateway_v6("wan");
605
		@file_put_contents("{$g['tmp_path']}/{$defaultifv6}_defaultgwv6", $gatewayipv6);
606
	}
607
	$dont_add_route = false;
608
	/* if OLSRD is enabled, allow WAN to house DHCP. */
609
	if (is_array($config['installedpackages']['olsrd'])) {
610
		foreach ($config['installedpackages']['olsrd']['config'] as $olsrd) {
611
			if (($olsrd['enabledyngw'] == "on") && ($olsrd['enable'] == "on")) {
612
				$dont_add_route = true;
613
				log_error(gettext("Not adding default route because OLSR dynamic gateway is enabled."));
614
				break;
615
			}
616
		}
617
	}
618

    
619
	$gateways_arr = return_gateways_array(false, true);
620
	foreach ($gateways_arr as $gateway) {
621
		// setup static interface routes for nonlocal gateways
622
		if (isset($gateway["nonlocalgateway"])) {
623
			$srgatewayip = $gateway['gateway'];
624
			$srinterfacegw = $gateway['interface'];
625
			if (is_ipaddr($srgatewayip) && !empty($srinterfacegw)) {
626
				$inet = (!is_ipaddrv4($srgatewayip) ? "-inet6" : "-inet");
627
				$cmd = "/sbin/route change {$inet} " . escapeshellarg($srgatewayip) . " ";
628
				mwexec($cmd . "-iface " . escapeshellarg($srinterfacegw));
629
				if (isset($config['system']['route-debug'])) {
630
					$mt = microtime();
631
					log_error("ROUTING debug: $mt - $cmd -iface $srinterfacegw ");
632
				}
633
			}
634
		}
635
	}
636

    
637
	if ($dont_add_route == false) {
638
		if (!empty($interface) && $interface != $interfacegw) {
639
			;
640
		} else if (is_ipaddrv4($gatewayip)) {
641
			log_error(sprintf(gettext("ROUTING: setting default route to %s"), $gatewayip));
642
			mwexec("/sbin/route change -inet default " . escapeshellarg($gatewayip));
643
		}
644

    
645
		if (!empty($interface) && $interface != $interfacegwv6) {
646
			;
647
		} else if (is_ipaddrv6($gatewayipv6)) {
648
			$ifscope = "";
649
			if (is_linklocal($gatewayipv6) && !strpos($gatewayipv6, '%')) {
650
				$ifscope = "%{$defaultifv6}";
651
			}
652
			log_error(sprintf(gettext("ROUTING: setting IPv6 default route to %s"), $gatewayipv6 . $ifscope));
653
			mwexec("/sbin/route change -inet6 default " . escapeshellarg("{$gatewayipv6}{$ifscope}"));
654
		}
655
	}
656

    
657
	system_staticroutes_configure($interface, false);
658

    
659
	return 0;
660
}
661

    
662
function system_staticroutes_configure($interface = "", $update_dns = false) {
663
	global $config, $g, $aliastable;
664

    
665
	$filterdns_list = array();
666

    
667
	$static_routes = get_staticroutes(false, true);
668
	if (count($static_routes)) {
669
		$gateways_arr = return_gateways_array(false, true);
670

    
671
		foreach ($static_routes as $rtent) {
672
			if (empty($gateways_arr[$rtent['gateway']])) {
673
				log_error(sprintf(gettext("Static Routes: Gateway IP could not be found for %s"), $rtent['network']));
674
				continue;
675
			}
676
			$gateway = $gateways_arr[$rtent['gateway']];
677
			if (!empty($interface) && $interface != $gateway['friendlyiface']) {
678
				continue;
679
			}
680

    
681
			$gatewayip = $gateway['gateway'];
682
			$interfacegw = $gateway['interface'];
683

    
684
			$blackhole = "";
685
			if (!strcasecmp("Null", substr($rtent['gateway'], 0, 3))) {
686
				$blackhole = "-blackhole";
687
			}
688

    
689
			if (!is_fqdn($rtent['network']) && !is_subnet($rtent['network'])) {
690
				continue;
691
			}
692

    
693
			$dnscache = array();
694
			if ($update_dns === true) {
695
				if (is_subnet($rtent['network'])) {
696
					continue;
697
				}
698
				$dnscache = explode("\n", trim(compare_hostname_to_dnscache($rtent['network'])));
699
				if (empty($dnscache)) {
700
					continue;
701
				}
702
			}
703

    
704
			if (is_subnet($rtent['network'])) {
705
				$ips = array($rtent['network']);
706
			} else {
707
				if (!isset($rtent['disabled'])) {
708
					$filterdns_list[] = $rtent['network'];
709
				}
710
				$ips = add_hostname_to_watch($rtent['network']);
711
			}
712

    
713
			foreach ($dnscache as $ip) {
714
				if (in_array($ip, $ips)) {
715
					continue;
716
				}
717
				mwexec("/sbin/route delete " . escapeshellarg($ip), true);
718
				if (isset($config['system']['route-debug'])) {
719
					$mt = microtime();
720
					log_error("ROUTING debug: $mt - route delete $ip ");
721
				}
722
			}
723

    
724
			if (isset($rtent['disabled'])) {
725
				/* XXX: This can break things by deleting routes that shouldn't be deleted - OpenVPN, dynamic routing scenarios, etc. redmine #3709 */
726
				foreach ($ips as $ip) {
727
					mwexec("/sbin/route delete " . escapeshellarg($ip), true);
728
					if (isset($config['system']['route-debug'])) {
729
						$mt = microtime();
730
						log_error("ROUTING debug: $mt - route delete $ip ");
731
					}
732
				}
733
				continue;
734
			}
735

    
736
			foreach ($ips as $ip) {
737
				if (is_ipaddrv4($ip)) {
738
					$ip .= "/32";
739
				}
740
				// do NOT do the same check here on v6, is_ipaddrv6 returns true when including the CIDR mask. doing so breaks v6 routes
741

    
742
				$inet = (is_subnetv6($ip) ? "-inet6" : "-inet");
743

    
744
				$cmd = "/sbin/route change {$inet} {$blackhole} " . escapeshellarg($ip) . " ";
745

    
746
				if (is_subnet($ip)) {
747
					if (is_ipaddr($gatewayip)) {
748
						mwexec($cmd . escapeshellarg($gatewayip));
749
						if (isset($config['system']['route-debug'])) {
750
							$mt = microtime();
751
							log_error("ROUTING debug: $mt - $cmd $gatewayip");
752
						}
753
					} else if (!empty($interfacegw)) {
754
						mwexec($cmd . "-iface " . escapeshellarg($interfacegw));
755
						if (isset($config['system']['route-debug'])) {
756
							$mt = microtime();
757
							log_error("ROUTING debug: $mt - $cmd -iface $interfacegw ");
758
						}
759
					}
760
				}
761
			}
762
		}
763
		unset($gateways_arr);
764
	}
765
	unset($static_routes);
766

    
767
	if ($update_dns === false) {
768
		if (count($filterdns_list)) {
769
			$interval = 60;
770
			$hostnames = "";
771
			array_unique($filterdns_list);
772
			foreach ($filterdns_list as $hostname) {
773
				$hostnames .= "cmd {$hostname} '/usr/local/sbin/pfSctl -c \"service reload routedns\"'\n";
774
			}
775
			file_put_contents("{$g['varetc_path']}/filterdns-route.hosts", $hostnames);
776
			unset($hostnames);
777

    
778
			if (isvalidpid("{$g['varrun_path']}/filterdns-route.pid")) {
779
				sigkillbypid("{$g['varrun_path']}/filterdns-route.pid", "HUP");
780
			} else {
781
				mwexec("/usr/local/sbin/filterdns -p {$g['varrun_path']}/filterdns-route.pid -i {$interval} -c {$g['varetc_path']}/filterdns-route.hosts -d 1");
782
			}
783
		} else {
784
			killbypid("{$g['varrun_path']}/filterdns-route.pid");
785
			@unlink("{$g['varrun_path']}/filterdns-route.pid");
786
		}
787
	}
788
	unset($filterdns_list);
789

    
790
	return 0;
791
}
792

    
793
function system_routing_enable() {
794
	global $config, $g;
795
	if (isset($config['system']['developerspew'])) {
796
		$mt = microtime();
797
		echo "system_routing_enable() being called $mt\n";
798
	}
799

    
800
	set_sysctl(array(
801
		"net.inet.ip.forwarding" => "1",
802
		"net.inet6.ip6.forwarding" => "1"
803
	));
804

    
805
	return;
806
}
807

    
808
function system_syslogd_fixup_server($server) {
809
	/* If it's an IPv6 IP alone, encase it in brackets */
810
	if (is_ipaddrv6($server)) {
811
		return "[$server]";
812
	} else {
813
		return $server;
814
	}
815
}
816

    
817
function system_syslogd_get_remote_servers($syslogcfg, $facility = "*.*") {
818
	// Rather than repeatedly use the same code, use this function to build a list of remote servers.
819
	$facility .= " ".
820
	$remote_servers = "";
821
	$pad_to  = max(strlen($facility), 56);
822
	$padding = ceil(($pad_to - strlen($facility))/8)+1;
823
	if (isset($syslogcfg['enable'])) {
824
		if ($syslogcfg['remoteserver']) {
825
			$remote_servers .= "{$facility}" . str_repeat("\t", $padding) . "@" . system_syslogd_fixup_server($syslogcfg['remoteserver']) . "\n";
826
		}
827
		if ($syslogcfg['remoteserver2']) {
828
			$remote_servers .= "{$facility}" . str_repeat("\t", $padding) . "@" . system_syslogd_fixup_server($syslogcfg['remoteserver2']) . "\n";
829
		}
830
		if ($syslogcfg['remoteserver3']) {
831
			$remote_servers .= "{$facility}" . str_repeat("\t", $padding) . "@" . system_syslogd_fixup_server($syslogcfg['remoteserver3']) . "\n";
832
		}
833
	}
834
	return $remote_servers;
835
}
836

    
837
function clear_log_file($logfile = "/var/log/system.log", $restart_syslogd = true) {
838
	global $config, $g;
839
	if ($restart_syslogd) {
840
		exec("/usr/bin/killall syslogd");
841
	}
842
	if (isset($config['system']['disablesyslogclog'])) {
843
		unlink($logfile);
844
		touch($logfile);
845
	} else {
846
		$log_size = isset($config['syslog']['logfilesize']) ? $config['syslog']['logfilesize'] : "511488";
847
		$log_size = isset($config['syslog'][basename($logfile, '.log') . '_settings']['logfilesize']) ? $config['syslog'][basename($logfile, '.log') . '_settings']['logfilesize'] : $log_size;
848
		exec("/usr/local/sbin/clog -i -s {$log_size} " . escapeshellarg($logfile));
849
	}
850
	if ($restart_syslogd) {
851
		system_syslogd_start();
852
	}
853
}
854

    
855
function clear_all_log_files($restart = false) {
856
	global $g;
857
	exec("/usr/bin/killall syslogd");
858

    
859
	$log_files = array("system", "filter", "dhcpd", "vpn", "pptps", "poes", "l2tps", "openvpn", "portalauth", "ipsec", "ppp", "relayd", "wireless", "nginx", "ntpd", "gateways", "resolver", "routing");
860
	foreach ($log_files as $lfile) {
861
		clear_log_file("{$g['varlog_path']}/{$lfile}.log", false);
862
	}
863

    
864
	if ($restart) {
865
		system_syslogd_start();
866
		killbyname("dhcpd");
867
		services_dhcpd_configure();
868
	}
869
	return;
870
}
871

    
872
function system_syslogd_start() {
873
	global $config, $g;
874
	if (isset($config['system']['developerspew'])) {
875
		$mt = microtime();
876
		echo "system_syslogd_start() being called $mt\n";
877
	}
878

    
879
	mwexec("/etc/rc.d/hostid start");
880

    
881
	$syslogcfg = $config['syslog'];
882

    
883
	if (platform_booting()) {
884
		echo gettext("Starting syslog...");
885
	}
886

    
887
	// Which logging type are we using this week??
888
	if (isset($config['system']['disablesyslogclog'])) {
889
		$log_directive = "";
890
		$log_create_directive = "/usr/bin/touch ";
891
		$log_size = "";
892
	} else { // Defaults to CLOG
893
		$log_directive = "%";
894
		$log_size = isset($config['syslog']['logfilesize']) ? $config['syslog']['logfilesize'] : "10240";
895
		$log_create_directive = "/usr/local/sbin/clog -i -s ";
896
	}
897

    
898
	$syslogd_extra = "";
899
	if (isset($syslogcfg)) {
900
		$separatelogfacilities = array('ntp', 'ntpd', 'ntpdate', 'charon', 'ipsec_starter', 'openvpn', 'pptps', 'poes', 'l2tps', 'relayd', 'hostapd', 'dnsmasq', 'filterdns', 'unbound', 'dhcpd', 'dhcrelay', 'dhclient', 'dhcp6c', 'dpinger', 'radvd', 'routed', 'olsrd', 'zebra', 'ospfd', 'bgpd', 'miniupnpd', 'filterlog');
901
		$syslogconf = "";
902
		if ($config['installedpackages']['package']) {
903
			foreach ($config['installedpackages']['package'] as $package) {
904
				if ($package['logging']) {
905
					array_push($separatelogfacilities, $package['logging']['facilityname']);
906
					if (!is_file($g['varlog_path'].'/'.$package['logging']['logfilename'])) {
907
						mwexec("{$log_create_directive} {$log_size} {$g['varlog_path']}/{$package['logging']['logfilename']}");
908
					}
909
					$syslogconf .= "!{$package['logging']['facilityname']}\n*.*\t\t\t\t\t\t {$log_directive}{$g['varlog_path']}/{$package['logging']['logfilename']}\n";
910
				}
911
			}
912
		}
913
		$facilitylist = implode(',', array_unique($separatelogfacilities));
914
		$syslogconf .= "!radvd,routed,olsrd,zebra,ospfd,bgpd,miniupnpd\n";
915
		if (!isset($syslogcfg['disablelocallogging'])) {
916
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/routing.log\n";
917
		}
918

    
919
		$syslogconf .= "!ntp,ntpd,ntpdate\n";
920
		if (!isset($syslogcfg['disablelocallogging'])) {
921
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/ntpd.log\n";
922
		}
923

    
924
		$syslogconf .= "!ppp\n";
925
		if (!isset($syslogcfg['disablelocallogging'])) {
926
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/ppp.log\n";
927
		}
928

    
929
		$syslogconf .= "!pptps\n";
930
		if (!isset($syslogcfg['disablelocallogging'])) {
931
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/pptps.log\n";
932
		}
933

    
934
		$syslogconf .= "!poes\n";
935
		if (!isset($syslogcfg['disablelocallogging'])) {
936
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/poes.log\n";
937
		}
938

    
939
		$syslogconf .= "!l2tps\n";
940
		if (!isset($syslogcfg['disablelocallogging'])) {
941
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/l2tps.log\n";
942
		}
943

    
944
		$syslogconf .= "!charon,ipsec_starter\n";
945
		if (!isset($syslogcfg['disablelocallogging'])) {
946
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/ipsec.log\n";
947
		}
948
		if (isset($syslogcfg['vpn'])) {
949
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "*.*");
950
		}
951

    
952
		$syslogconf .= "!openvpn\n";
953
		if (!isset($syslogcfg['disablelocallogging'])) {
954
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/openvpn.log\n";
955
		}
956
		if (isset($syslogcfg['vpn'])) {
957
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "*.*");
958
		}
959

    
960
		$syslogconf .= "!dpinger\n";
961
		if (!isset($syslogcfg['disablelocallogging'])) {
962
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/gateways.log\n";
963
		}
964
		if (isset($syslogcfg['dpinger'])) {
965
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "*.*");
966
		}
967

    
968
		$syslogconf .= "!dnsmasq,filterdns,unbound\n";
969
		if (!isset($syslogcfg['disablelocallogging'])) {
970
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/resolver.log\n";
971
		}
972

    
973
		$syslogconf .= "!dhcpd,dhcrelay,dhclient,dhcp6c,dhcpleases,dhcpleases6\n";
974
		if (!isset($syslogcfg['disablelocallogging'])) {
975
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/dhcpd.log\n";
976
		}
977
		if (isset($syslogcfg['dhcp'])) {
978
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "*.*");
979
		}
980

    
981
		$syslogconf .= "!relayd\n";
982
		if (!isset($syslogcfg['disablelocallogging'])) {
983
			$syslogconf .= "*.* 								{$log_directive}{$g['varlog_path']}/relayd.log\n";
984
		}
985
		if (isset($syslogcfg['relayd'])) {
986
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "*.*");
987
		}
988

    
989
		$syslogconf .= "!hostapd\n";
990
		if (!isset($syslogcfg['disablelocallogging'])) {
991
			$syslogconf .= "*.* 								{$log_directive}{$g['varlog_path']}/wireless.log\n";
992
		}
993
		if (isset($syslogcfg['hostapd'])) {
994
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "*.*");
995
		}
996

    
997
		$syslogconf .= "!filterlog\n";
998
		if (!isset($syslogcfg['disablelocallogging'])) {
999
			$syslogconf .= "*.* 								{$log_directive}{$g['varlog_path']}/filter.log\n";
1000
		}
1001

    
1002
		if (isset($syslogcfg['filter'])) {
1003
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "*.*");
1004
		}
1005

    
1006
		$syslogconf .= "!-{$facilitylist}\n";
1007
		if (!isset($syslogcfg['disablelocallogging'])) {
1008
			$syslogconf .= <<<EOD
1009
local3.*							{$log_directive}{$g['varlog_path']}/vpn.log
1010
local4.*							{$log_directive}{$g['varlog_path']}/portalauth.log
1011
local5.*							{$log_directive}{$g['varlog_path']}/nginx.log
1012
local7.*							{$log_directive}{$g['varlog_path']}/dhcpd.log
1013
*.notice;kern.debug;lpr.info;mail.crit;daemon.none;news.err;local0.none;local3.none;local4.none;local7.none;security.*;auth.info;authpriv.info;daemon.info	{$log_directive}{$g['varlog_path']}/system.log
1014
auth.info;authpriv.info 					|exec /usr/local/sbin/sshlockout_pf 15
1015
*.emerg								*
1016

    
1017
EOD;
1018
		}
1019
		if (isset($syslogcfg['vpn'])) {
1020
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "local3.*");
1021
		}
1022
		if (isset($syslogcfg['portalauth'])) {
1023
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "local4.*");
1024
		}
1025
		if (isset($syslogcfg['dhcp'])) {
1026
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "local7.*");
1027
		}
1028
		if (isset($syslogcfg['system'])) {
1029
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "*.emerg;*.notice;kern.debug;lpr.info;mail.crit;news.err;local0.none;local3.none;local7.none;security.*;auth.info;authpriv.info;daemon.info");
1030
		}
1031
		if (isset($syslogcfg['logall'])) {
1032
			// Make everything mean everything, including facilities excluded above.
1033
			$syslogconf .= "!*\n";
1034
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "*.*");
1035
		}
1036

    
1037
		if (isset($syslogcfg['zmqserver'])) {
1038
				$syslogconf .= <<<EOD
1039
*.*								^{$syslogcfg['zmqserver']}
1040

    
1041
EOD;
1042
		}
1043
		/* write syslog.conf */
1044
		if (!@file_put_contents("{$g['varetc_path']}/syslog.conf", $syslogconf)) {
1045
			printf(gettext("Error: cannot open syslog.conf in system_syslogd_start().%s"), "\n");
1046
			unset($syslogconf);
1047
			return 1;
1048
		}
1049
		unset($syslogconf);
1050

    
1051
		// Ensure that the log directory exists
1052
		if (!is_dir("{$g['dhcpd_chroot_path']}/var/run")) {
1053
			exec("/bin/mkdir -p {$g['dhcpd_chroot_path']}/var/run");
1054
		}
1055

    
1056
		$sourceip = "";
1057
		if (!empty($syslogcfg['sourceip'])) {
1058
			if ($syslogcfg['ipproto'] == "ipv6") {
1059
				$ifaddr = is_ipaddr($syslogcfg['sourceip']) ? $syslogcfg['sourceip'] : get_interface_ipv6($syslogcfg['sourceip']);
1060
				if (!is_ipaddr($ifaddr)) {
1061
					$ifaddr = get_interface_ip($syslogcfg['sourceip']);
1062
				}
1063
			} else {
1064
				$ifaddr = is_ipaddr($syslogcfg['sourceip']) ? $syslogcfg['sourceip'] : get_interface_ip($syslogcfg['sourceip']);
1065
				if (!is_ipaddr($ifaddr)) {
1066
					$ifaddr = get_interface_ipv6($syslogcfg['sourceip']);
1067
				}
1068
			}
1069
			if (is_ipaddr($ifaddr)) {
1070
				$sourceip = "-b {$ifaddr}";
1071
			}
1072
		}
1073

    
1074
		$syslogd_extra = "-f {$g['varetc_path']}/syslog.conf {$sourceip}";
1075
	}
1076

    
1077
	if (isvalidpid("{$g['varrun_path']}/syslog.pid")) {
1078
		sigkillbypid("{$g['varrun_path']}/syslog.pid", "TERM");
1079
		usleep(100000); // syslogd often doesn't respond to a TERM quickly enough for the starting of syslogd below to be successful
1080
	}
1081

    
1082
	if (isvalidpid("{$g['varrun_path']}/syslog.pid")) {
1083
		// if it still hasn't responded to the TERM, KILL it.
1084
		sigkillbypid("{$g['varrun_path']}/syslog.pid", "KILL");
1085
		usleep(100000);
1086
	}
1087

    
1088

    
1089
	$retval = mwexec_bg("/usr/sbin/syslogd -s -c -c -l {$g['dhcpd_chroot_path']}/var/run/log -P {$g['varrun_path']}/syslog.pid {$syslogd_extra}");
1090

    
1091
	if (platform_booting()) {
1092
		echo gettext("done.") . "\n";
1093
	}
1094

    
1095
	return $retval;
1096
}
1097

    
1098
function system_webgui_create_certificate() {
1099
	global $config, $g;
1100

    
1101
	if (!is_array($config['ca'])) {
1102
		$config['ca'] = array();
1103
	}
1104
	$a_ca =& $config['ca'];
1105
	if (!is_array($config['cert'])) {
1106
		$config['cert'] = array();
1107
	}
1108
	$a_cert =& $config['cert'];
1109
	log_error(gettext("Creating SSL Certificate for this host"));
1110

    
1111
	$cert = array();
1112
	$cert['refid'] = uniqid();
1113
	$cert['descr'] = sprintf(gettext("webConfigurator default (%s)"), $cert['refid']);
1114

    
1115
	$dn = array(
1116
		'countryName' => "US",
1117
		'stateOrProvinceName' => "State",
1118
		'localityName' => "Locality",
1119
		'organizationName' => "{$g['product_name']} webConfigurator Self-Signed Certificate",
1120
		'emailAddress' => "admin@{$config['system']['hostname']}.{$config['system']['domain']}",
1121
		'commonName' => "{$config['system']['hostname']}-{$cert['refid']}");
1122
	$old_err_level = error_reporting(0); /* otherwise openssl_ functions throw warnings directly to a page screwing menu tab */
1123
	if (!cert_create($cert, null, 2048, 2000, $dn, "self-signed", "sha256")) {
1124
		while ($ssl_err = openssl_error_string()) {
1125
			log_error(sprintf(gettext("Error creating WebGUI Certificate: openssl library returns: %s"), $ssl_err));
1126
		}
1127
		error_reporting($old_err_level);
1128
		return null;
1129
	}
1130
	error_reporting($old_err_level);
1131

    
1132
	$a_cert[] = $cert;
1133
	$config['system']['webgui']['ssl-certref'] = $cert['refid'];
1134
	write_config(sprintf(gettext("Generated new self-signed HTTPS certificate (%s)"), $cert['refid']));
1135
	return $cert;
1136
}
1137

    
1138
function system_webgui_start() {
1139
	global $config, $g;
1140

    
1141
	if (platform_booting()) {
1142
		echo gettext("Starting webConfigurator...");
1143
	}
1144

    
1145
	chdir($g['www_path']);
1146

    
1147
	/* defaults */
1148
	$portarg = "80";
1149
	$crt = "";
1150
	$key = "";
1151
	$ca = "";
1152

    
1153
	/* non-standard port? */
1154
	if (isset($config['system']['webgui']['port']) && $config['system']['webgui']['port'] <> "") {
1155
		$portarg = "{$config['system']['webgui']['port']}";
1156
	}
1157

    
1158
	if ($config['system']['webgui']['protocol'] == "https") {
1159
		// Ensure that we have a webConfigurator CERT
1160
		$cert =& lookup_cert($config['system']['webgui']['ssl-certref']);
1161
		if (!is_array($cert) || !$cert['crt'] || !$cert['prv']) {
1162
			$cert = system_webgui_create_certificate();
1163
		}
1164
		$crt = base64_decode($cert['crt']);
1165
		$key = base64_decode($cert['prv']);
1166

    
1167
		if (!$config['system']['webgui']['port']) {
1168
			$portarg = "443";
1169
		}
1170
		$ca = ca_chain($cert);
1171
	}
1172

    
1173
	/* generate nginx configuration */
1174
	system_generate_nginx_config("{$g['varetc_path']}/nginx-webConfigurator.conf",
1175
		$crt, $key, $ca, "nginx-webConfigurator.pid", $portarg, "/usr/local/www/",
1176
		"cert.crt", "cert.key");
1177

    
1178
	/* kill any running nginx */
1179
	killbypid("{$g['varrun_path']}/nginx-webConfigurator.pid");
1180

    
1181
	sleep(1);
1182

    
1183
	@unlink("{$g['varrun_path']}/nginx-webConfigurator.pid");
1184

    
1185
	/* start nginx */
1186
	$res = mwexec("/usr/local/sbin/nginx -c {$g['varetc_path']}/nginx-webConfigurator.conf");
1187

    
1188
	if (platform_booting()) {
1189
		if ($res == 0) {
1190
			echo gettext("done.") . "\n";
1191
		} else {
1192
			echo gettext("failed!") . "\n";
1193
		}
1194
	}
1195

    
1196
	return $res;
1197
}
1198

    
1199
function system_generate_nginx_config($filename,
1200
	$cert,
1201
	$key,
1202
	$ca,
1203
	$pid_file,
1204
	$port = 80,
1205
	$document_root = "/usr/local/www/",
1206
	$cert_location = "cert.crt",
1207
	$key_location = "cert.key",
1208
	$captive_portal = false) {
1209

    
1210
	global $config, $g;
1211

    
1212
	if (isset($config['system']['developerspew'])) {
1213
		$mt = microtime();
1214
		echo "system_generate_nginx_config() being called $mt\n";
1215
	}
1216

    
1217
	if ($captive_portal !== false) {
1218
		$cp_interfaces = explode(",", $config['captiveportal'][$captive_portal]['interface']);
1219
		$cp_hostcheck = "";
1220
		foreach ($cp_interfaces as $cpint) {
1221
			$cpint_ip = get_interface_ip($cpint);
1222
			if (is_ipaddr($cpint_ip)) {
1223
				$cp_hostcheck .= "\t\tif (\$http_host ~* $cpint_ip) {\n";
1224
				$cp_hostcheck .= "\t\t\tset \$cp_redirect no;\n";
1225
				$cp_hostcheck .= "\t\t}\n";
1226
			}
1227
		}
1228
		if (isset($config['captiveportal'][$captive_portal]['httpsname']) &&
1229
		    is_domain($config['captiveportal'][$captive_portal]['httpsname'])) {
1230
			$cp_hostcheck .= "\t\tif (\$http_host ~* {$config['captiveportal'][$captive_portal]['httpsname']}) {\n";
1231
			$cp_hostcheck .= "\t\t\tset \$cp_redirect no;\n";
1232
			$cp_hostcheck .= "\t\t}\n";
1233
		}
1234
		$cp_rewrite = "\t\tif (\$cp_redirect = '') {\n";
1235
		$cp_rewrite .= "\t\t\trewrite	^ /index.php?zone=$captive_portal&redirurl=\$request_uri break;\n";
1236
		$cp_rewrite .= "\t\t}\n";
1237

    
1238
		$maxprocperip = $config['captiveportal'][$captive_portal]['maxprocperip'];
1239
		if (empty($maxprocperip)) {
1240
			$maxprocperip = 10;
1241
		}
1242
		$captive_portal_maxprocperip = "\t\tlimit_conn addr $maxprocperip;\n";
1243
	}
1244

    
1245
	if (empty($port)) {
1246
		$nginx_port = "80";
1247
	} else {
1248
		$nginx_port = $port;
1249
	}
1250

    
1251
	$memory = get_memory();
1252
	$realmem = $memory[1];
1253

    
1254
	// Determine web GUI process settings and take into account low memory systems
1255
	if ($realmem < 255) {
1256
		$max_procs = 1;
1257
	} else {
1258
		$max_procs = ($config['system']['webgui']['max_procs']) ? $config['system']['webgui']['max_procs'] : 2;
1259
	}
1260

    
1261
	// Ramp up captive portal max procs, assuming each PHP process can consume up to 64MB RAM
1262
	if ($captive_portal !== false) {
1263
		if ($realmem > 135 and $realmem < 256) {
1264
			$max_procs += 1; // 2 worker processes
1265
		} else if ($realmem > 255 and $realmem < 513) {
1266
			$max_procs += 2; // 3 worker processes
1267
		} else if ($realmem > 512) {
1268
			$max_procs += 4; // 6 worker processes
1269
		}
1270
	}
1271

    
1272
	$nginx_config = <<<EOD
1273
#
1274
# nginx configuration file
1275

    
1276
pid {$g['varrun_path']}/{$pid_file};
1277

    
1278
user  root wheel;
1279
worker_processes  {$max_procs};
1280

    
1281
EOD;
1282

    
1283
	if (!isset($config['syslog']['nolognginx'])) {
1284
		$nginx_config .= "error_log  syslog:server=unix:/var/run/log,facility=local5;\n";
1285
	}
1286

    
1287
	$nginx_config .= <<<EOD
1288

    
1289
events {
1290
    worker_connections  1024;
1291
}
1292

    
1293
http {
1294
	include       /usr/local/etc/nginx/mime.types;
1295
	default_type  application/octet-stream;
1296
	add_header X-Frame-Options SAMEORIGIN;
1297
	server_tokens off;
1298

    
1299
	sendfile        on;
1300

    
1301
	access_log      syslog:server=unix:/var/run/log,facility=local5 combined;
1302

    
1303
EOD;
1304

    
1305
	if ($captive_portal !== false) {
1306
		$nginx_config .= "\tlimit_conn_zone \$binary_remote_addr zone=addr:10m;\n";
1307
		$nginx_config .= "\tkeepalive_timeout 0;\n";
1308
	} else {
1309
		$nginx_config .= "\tkeepalive_timeout 75;\n";
1310
	}
1311

    
1312
	if ($cert <> "" and $key <> "") {
1313
		$nginx_config .= "\n";
1314
		$nginx_config .= "\tserver {\n";
1315
		$nginx_config .= "\t\tlisten {$nginx_port} ssl;\n";
1316
		$nginx_config .= "\t\tlisten [::]:{$nginx_port} ssl;\n";
1317
		$nginx_config .= "\n";
1318
		$nginx_config .= "\t\tssl_certificate         {$g['varetc_path']}/{$cert_location};\n";
1319
		$nginx_config .= "\t\tssl_certificate_key     {$g['varetc_path']}/{$key_location};\n";
1320
		$nginx_config .= "\t\tssl_session_timeout     10m;\n";
1321
		$nginx_config .= "\t\tkeepalive_timeout       70;\n";
1322
		$nginx_config .= "\t\tssl_session_cache       shared:SSL:10m;\n";
1323
		if ($captive_portal !== false) {
1324
			// leave TLSv1.0 for CP for now for compatibility
1325
			$nginx_config .= "\t\tssl_protocols   TLSv1 TLSv1.1 TLSv1.2;\n";
1326
		} else {
1327
			$nginx_config .= "\t\tssl_protocols   TLSv1.1 TLSv1.2;\n";
1328
		}
1329
		$nginx_config .= "\t\tssl_ciphers \"EECDH+AESGCM:EDH+AESGCM:AES256+EECDH:AES256+EDH\";\n";
1330
		$nginx_config .= "\t\tssl_prefer_server_ciphers       on;\n";
1331
		$nginx_config .= "\t\tadd_header Strict-Transport-Security \"max-age=31536000\";\n";
1332
		$nginx_config .= "\t\tadd_header X-Content-Type-Options nosniff;\n";
1333
		$nginx_config .= "\t\tssl_session_tickets off;\n";
1334
		$nginx_config .= "\t\tssl_dhparam /etc/dh-parameters.4096;\n";
1335
	} else {
1336
		$nginx_config .= "\n";
1337
		$nginx_config .= "\tserver {\n";
1338
		$nginx_config .= "\t\tlisten {$nginx_port};\n";
1339
		$nginx_config .= "\t\tlisten [::]:{$nginx_port};\n";
1340
	}
1341

    
1342
	$nginx_config .= <<<EOD
1343

    
1344
		client_max_body_size 200m;
1345

    
1346
		gzip on;
1347
		gzip_types text/plain text/css text/javascript application/x-javascript text/xml application/xml application/xml+rss application/json;
1348

    
1349

    
1350
EOD;
1351

    
1352
	if ($captive_portal !== false) {
1353
		$nginx_config .= <<<EOD
1354
$captive_portal_maxprocperip
1355
$cp_hostcheck
1356
$cp_rewrite
1357
		log_not_found off;
1358

    
1359
EOD;
1360

    
1361
	}
1362

    
1363
	$nginx_config .= <<<EOD
1364
		root "{$document_root}";
1365
		location / {
1366
			index  index.php index.html index.htm;
1367
		}
1368

    
1369
		location ~ \.php$ {
1370
			try_files \$uri =404; #  This line closes a potential security hole
1371
			# ensuring users can't execute uploaded files
1372
			# see: http://forum.nginx.org/read.php?2,88845,page=3
1373
			fastcgi_pass   unix:{$g['varrun_path']}/php-fpm.socket;
1374
			fastcgi_index  index.php;
1375
			fastcgi_param  SCRIPT_FILENAME  \$document_root\$fastcgi_script_name;
1376
			fastcgi_read_timeout 180;
1377
			include        /usr/local/etc/nginx/fastcgi_params;
1378
		}
1379
	}
1380

    
1381
EOD;
1382

    
1383
	$cert = str_replace("\r", "", $cert);
1384
	$key = str_replace("\r", "", $key);
1385

    
1386
	$cert = str_replace("\n\n", "\n", $cert);
1387
	$key = str_replace("\n\n", "\n", $key);
1388

    
1389
	if ($cert <> "" and $key <> "") {
1390
		$fd = fopen("{$g['varetc_path']}/{$cert_location}", "w");
1391
		if (!$fd) {
1392
			printf(gettext("Error: cannot open certificate file in system_webgui_start().%s"), "\n");
1393
			return 1;
1394
		}
1395
		chmod("{$g['varetc_path']}/{$cert_location}", 0600);
1396
		if ($ca <> "") {
1397
			$cert_chain = $cert . "\n" . $ca;
1398
		} else {
1399
			$cert_chain = $cert;
1400
		}
1401
		fwrite($fd, $cert_chain);
1402
		fclose($fd);
1403
		$fd = fopen("{$g['varetc_path']}/{$key_location}", "w");
1404
		if (!$fd) {
1405
			printf(gettext("Error: cannot open certificate key file in system_webgui_start().%s"), "\n");
1406
			return 1;
1407
		}
1408
		chmod("{$g['varetc_path']}/{$key_location}", 0600);
1409
		fwrite($fd, $key);
1410
		fclose($fd);
1411
	}
1412

    
1413
	// Add HTTP to HTTPS redirect
1414
	if ($captive_portal === false && $config['system']['webgui']['protocol'] == "https" && !isset($config['system']['webgui']['disablehttpredirect'])) {
1415
		if ($nginx_port != "443") {
1416
			$redirectport = ":{$nginx_port}";
1417
		}
1418
		$nginx_config .= <<<EOD
1419
	server {
1420
		listen 80;
1421
		listen [::]:80;
1422
		return 301 https://\$http_host$redirectport\$request_uri;
1423
	}
1424

    
1425
EOD;
1426
	}
1427

    
1428
	$nginx_config .= "}\n";
1429

    
1430
	$fd = fopen("{$filename}", "w");
1431
	if (!$fd) {
1432
		printf(gettext("Error: cannot open %s in system_generate_nginx_config().%s"), $filename, "\n");
1433
		return 1;
1434
	}
1435
	fwrite($fd, $nginx_config);
1436
	fclose($fd);
1437

    
1438
	/* nginx will fail to start if this directory does not exist. */
1439
	safe_mkdir("/var/tmp/nginx/");
1440

    
1441
	return 0;
1442

    
1443
}
1444

    
1445
function system_get_timezone_list() {
1446
	global $g;
1447

    
1448
	$file_list = array_merge(
1449
		glob("/usr/share/zoneinfo/[A-Z]*"),
1450
		glob("/usr/share/zoneinfo/*/*"),
1451
		glob("/usr/share/zoneinfo/*/*/*")
1452
	);
1453

    
1454
	if (empty($file_list)) {
1455
		$file_list[] = $g['default_timezone'];
1456
	} else {
1457
		/* Remove directories from list */
1458
		$file_list = array_filter($file_list, function($v) {
1459
			return !is_dir($v);
1460
		});
1461
	}
1462

    
1463
	/* Remove directory prefix */
1464
	$file_list = str_replace('/usr/share/zoneinfo/', '', $file_list);
1465

    
1466
	sort($file_list);
1467

    
1468
	return $file_list;
1469
}
1470

    
1471
function system_timezone_configure() {
1472
	global $config, $g;
1473
	if (isset($config['system']['developerspew'])) {
1474
		$mt = microtime();
1475
		echo "system_timezone_configure() being called $mt\n";
1476
	}
1477

    
1478
	$syscfg = $config['system'];
1479

    
1480
	if (platform_booting()) {
1481
		echo gettext("Setting timezone...");
1482
	}
1483

    
1484
	/* extract appropriate timezone file */
1485
	$timezone = (isset($syscfg['timezone']) ? $syscfg['timezone'] : $g['default_timezone']);
1486
	conf_mount_rw();
1487
	/* DO NOT remove \n otherwise tzsetup will fail */
1488
	@file_put_contents("/var/db/zoneinfo", $timezone . "\n");
1489
	mwexec("/usr/sbin/tzsetup -r");
1490
	conf_mount_ro();
1491

    
1492
	if (platform_booting()) {
1493
		echo gettext("done.") . "\n";
1494
	}
1495
}
1496

    
1497
function system_ntp_setup_gps($serialport) {
1498
	global $config, $g;
1499
	$gps_device = '/dev/gps0';
1500
	$serialport = '/dev/'.$serialport;
1501

    
1502
	if (!file_exists($serialport)) {
1503
		return false;
1504
	}
1505

    
1506
	conf_mount_rw();
1507
	// Create symlink that ntpd requires
1508
	unlink_if_exists($gps_device);
1509
	@symlink($serialport, $gps_device);
1510

    
1511
	$gpsbaud = '4800';
1512
	if (is_array($config['ntpd']) && is_array($config['ntpd']['gps']) && !empty($config['ntpd']['gps']['speed'])) {
1513
		switch ($config['ntpd']['gps']['speed']) {
1514
			case '16':
1515
				$gpsbaud = '9600';
1516
				break;
1517
			case '32':
1518
				$gpsbaud = '19200';
1519
				break;
1520
			case '48':
1521
				$gpsbaud = '38400';
1522
				break;
1523
			case '64':
1524
				$gpsbaud = '57600';
1525
				break;
1526
			case '80':
1527
				$gpsbaud = '115200';
1528
				break;
1529
		}
1530
	}
1531

    
1532
	/* Configure the serial port for raw IO and set the speed */
1533
	mwexec("stty -f {$serialport}.init raw speed {$gpsbaud}");
1534

    
1535
	/* Send the following to the GPS port to initialize the GPS */
1536
	if (is_array($config['ntpd']) && is_array($config['ntpd']['gps']) && !empty($config['ntpd']['gps']['type'])) {
1537
		$gps_init = base64_decode($config['ntpd']['gps']['initcmd']);
1538
	} else {
1539
		$gps_init = base64_decode('JFBVQlgsNDAsR1NWLDAsMCwwLDAqNTkNCiRQVUJYLDQwLEdMTCwwLDAsMCwwKjVDDQokUFVCWCw0MCxaREEsMCwwLDAsMCo0NA0KJFBVQlgsNDAsVlRHLDAsMCwwLDAqNUUNCiRQVUJYLDQwLEdTViwwLDAsMCwwKjU5DQokUFVCWCw0MCxHU0EsMCwwLDAsMCo0RQ0KJFBVQlgsNDAsR0dBLDAsMCwwLDANCiRQVUJYLDQwLFRYVCwwLDAsMCwwDQokUFVCWCw0MCxSTUMsMCwwLDAsMCo0Ng0KJFBVQlgsNDEsMSwwMDA3LDAwMDMsNDgwMCwwDQokUFVCWCw0MCxaREEsMSwxLDEsMQ==');
1540
	}
1541

    
1542
	/* XXX: Why not file_put_contents to the device */
1543
	@file_put_contents('/tmp/gps.init', $gps_init);
1544
	mwexec("cat /tmp/gps.init > {$serialport}");
1545

    
1546
	/* Add /etc/remote entry in case we need to read from the GPS with tip */
1547
	if (intval(`grep -c '^gps0' /etc/remote`) == 0) {
1548
		@file_put_contents("/etc/remote", "gps0:dv={$serialport}:br#{$gpsbaud}:pa=none:", FILE_APPEND);
1549
	}
1550

    
1551
	conf_mount_ro();
1552

    
1553
	return true;
1554
}
1555

    
1556
function system_ntp_setup_pps($serialport) {
1557
	global $config, $g;
1558

    
1559
	$pps_device = '/dev/pps0';
1560
	$serialport = '/dev/'.$serialport;
1561

    
1562
	if (!file_exists($serialport)) {
1563
		return false;
1564
	}
1565

    
1566
	conf_mount_rw();
1567
	// Create symlink that ntpd requires
1568
	unlink_if_exists($pps_device);
1569
	@symlink($serialport, $pps_device);
1570

    
1571
	conf_mount_ro();
1572

    
1573
	return true;
1574
}
1575

    
1576

    
1577
function system_ntp_configure() {
1578
	global $config, $g;
1579

    
1580
	$driftfile = "/var/db/ntpd.drift";
1581
	$statsdir = "/var/log/ntp";
1582
	$gps_device = '/dev/gps0';
1583

    
1584
	safe_mkdir($statsdir);
1585

    
1586
	if (!is_array($config['ntpd'])) {
1587
		$config['ntpd'] = array();
1588
	}
1589

    
1590
	$ntpcfg = "# \n";
1591
	$ntpcfg .= "# pfSense ntp configuration file \n";
1592
	$ntpcfg .= "# \n\n";
1593
	$ntpcfg .= "tinker panic 0 \n";
1594

    
1595
	/* Add Orphan mode */
1596
	$ntpcfg .= "# Orphan mode stratum\n";
1597
	$ntpcfg .= 'tos orphan ';
1598
	if (!empty($config['ntpd']['orphan'])) {
1599
		$ntpcfg .= $config['ntpd']['orphan'];
1600
	} else {
1601
		$ntpcfg .= '12';
1602
	}
1603
	$ntpcfg .= "\n";
1604

    
1605
	/* Add PPS configuration */
1606
	if (is_array($config['ntpd']['pps']) && !empty($config['ntpd']['pps']['port']) &&
1607
	    file_exists('/dev/'.$config['ntpd']['pps']['port']) &&
1608
	    system_ntp_setup_pps($config['ntpd']['pps']['port'])) {
1609
		$ntpcfg .= "\n";
1610
		$ntpcfg .= "# PPS Setup\n";
1611
		$ntpcfg .= 'server 127.127.22.0';
1612
		$ntpcfg .= ' minpoll 4 maxpoll 4';
1613
		if (empty($config['ntpd']['pps']['prefer'])) { /*note: this one works backwards */
1614
			$ntpcfg .= ' prefer';
1615
		}
1616
		if (!empty($config['ntpd']['pps']['noselect'])) {
1617
			$ntpcfg .= ' noselect ';
1618
		}
1619
		$ntpcfg .= "\n";
1620
		$ntpcfg .= 'fudge 127.127.22.0';
1621
		if (!empty($config['ntpd']['pps']['fudge1'])) {
1622
			$ntpcfg .= ' time1 ';
1623
			$ntpcfg .= $config['ntpd']['pps']['fudge1'];
1624
		}
1625
		if (!empty($config['ntpd']['pps']['flag2'])) {
1626
			$ntpcfg .= ' flag2 1';
1627
		}
1628
		if (!empty($config['ntpd']['pps']['flag3'])) {
1629
			$ntpcfg .= ' flag3 1';
1630
		} else {
1631
			$ntpcfg .= ' flag3 0';
1632
		}
1633
		if (!empty($config['ntpd']['pps']['flag4'])) {
1634
			$ntpcfg .= ' flag4 1';
1635
		}
1636
		if (!empty($config['ntpd']['pps']['refid'])) {
1637
			$ntpcfg .= ' refid ';
1638
			$ntpcfg .= $config['ntpd']['pps']['refid'];
1639
		}
1640
		$ntpcfg .= "\n";
1641
	}
1642
	/* End PPS configuration */
1643

    
1644
	/* Add GPS configuration */
1645
	if (is_array($config['ntpd']['gps']) && !empty($config['ntpd']['gps']['port']) &&
1646
	    file_exists('/dev/'.$config['ntpd']['gps']['port']) &&
1647
	    system_ntp_setup_gps($config['ntpd']['gps']['port'])) {
1648
		$ntpcfg .= "\n";
1649
		$ntpcfg .= "# GPS Setup\n";
1650
		$ntpcfg .= 'server 127.127.20.0 mode ';
1651
		if (!empty($config['ntpd']['gps']['nmea']) || !empty($config['ntpd']['gps']['speed']) || !empty($config['ntpd']['gps']['subsec'])) {
1652
			if (!empty($config['ntpd']['gps']['nmea'])) {
1653
				$ntpmode = (int) $config['ntpd']['gps']['nmea'];
1654
			}
1655
			if (!empty($config['ntpd']['gps']['speed'])) {
1656
				$ntpmode += (int) $config['ntpd']['gps']['speed'];
1657
			}
1658
			if (!empty($config['ntpd']['gps']['subsec'])) {
1659
				$ntpmode += 128;
1660
			}
1661
			$ntpcfg .= (string) $ntpmode;
1662
		} else {
1663
			$ntpcfg .= '0';
1664
		}
1665
		$ntpcfg .= ' minpoll 4 maxpoll 4';
1666
		if (empty($config['ntpd']['gps']['prefer'])) { /*note: this one works backwards */
1667
			$ntpcfg .= ' prefer';
1668
		}
1669
		if (!empty($config['ntpd']['gps']['noselect'])) {
1670
			$ntpcfg .= ' noselect ';
1671
		}
1672
		$ntpcfg .= "\n";
1673
		$ntpcfg .= 'fudge 127.127.20.0';
1674
		if (!empty($config['ntpd']['gps']['fudge1'])) {
1675
			$ntpcfg .= ' time1 ';
1676
			$ntpcfg .= $config['ntpd']['gps']['fudge1'];
1677
		}
1678
		if (!empty($config['ntpd']['gps']['fudge2'])) {
1679
			$ntpcfg .= ' time2 ';
1680
			$ntpcfg .= $config['ntpd']['gps']['fudge2'];
1681
		}
1682
		if (!empty($config['ntpd']['gps']['flag1'])) {
1683
			$ntpcfg .= ' flag1 1';
1684
		} else {
1685
			$ntpcfg .= ' flag1 0';
1686
		}
1687
		if (!empty($config['ntpd']['gps']['flag2'])) {
1688
			$ntpcfg .= ' flag2 1';
1689
		}
1690
		if (!empty($config['ntpd']['gps']['flag3'])) {
1691
			$ntpcfg .= ' flag3 1';
1692
		} else {
1693
			$ntpcfg .= ' flag3 0';
1694
		}
1695
		if (!empty($config['ntpd']['gps']['flag4'])) {
1696
			$ntpcfg .= ' flag4 1';
1697
		}
1698
		if (!empty($config['ntpd']['gps']['refid'])) {
1699
			$ntpcfg .= ' refid ';
1700
			$ntpcfg .= $config['ntpd']['gps']['refid'];
1701
		}
1702
		if (!empty($config['ntpd']['gps']['stratum'])) {
1703
			$ntpcfg .= ' stratum ';
1704
			$ntpcfg .= $config['ntpd']['gps']['stratum'];
1705
		}
1706
		$ntpcfg .= "\n";
1707
	} elseif (is_array($config['ntpd']) && !empty($config['ntpd']['gpsport']) &&
1708
	    file_exists('/dev/'.$config['ntpd']['gpsport']) &&
1709
	    system_ntp_setup_gps($config['ntpd']['gpsport'])) {
1710
		/* This handles a 2.1 and earlier config */
1711
		$ntpcfg .= "# GPS Setup\n";
1712
		$ntpcfg .= "server 127.127.20.0 mode 0 minpoll 4 maxpoll 4 prefer\n";
1713
		$ntpcfg .= "fudge 127.127.20.0 time1 0.155 time2 0.000 flag1 1 flag2 0 flag3 1\n";
1714
		// Fall back to local clock if GPS is out of sync?
1715
		$ntpcfg .= "server 127.127.1.0\n";
1716
		$ntpcfg .= "fudge 127.127.1.0 stratum 12\n";
1717
	}
1718
	/* End GPS configuration */
1719

    
1720
	$ntpcfg .= "\n\n# Upstream Servers\n";
1721
	/* foreach through ntp servers and write out to ntpd.conf */
1722
	foreach (explode(' ', $config['system']['timeservers']) as $ts) {
1723
		$ntpcfg .= "server {$ts} iburst maxpoll 9";
1724
		if (substr_count($config['ntpd']['prefer'], $ts)) {
1725
			$ntpcfg .= ' prefer';
1726
		}
1727
		if (substr_count($config['ntpd']['noselect'], $ts)) {
1728
			$ntpcfg .= ' noselect';
1729
		}
1730
		$ntpcfg .= "\n";
1731
	}
1732
	unset($ts);
1733

    
1734
	$ntpcfg .= "\n\n";
1735
	if (!empty($config['ntpd']['clockstats']) || !empty($config['ntpd']['loopstats']) || !empty($config['ntpd']['peerstats'])) {
1736
		$ntpcfg .= "enable stats\n";
1737
		$ntpcfg .= 'statistics';
1738
		if (!empty($config['ntpd']['clockstats'])) {
1739
			$ntpcfg .= ' clockstats';
1740
		}
1741
		if (!empty($config['ntpd']['loopstats'])) {
1742
			$ntpcfg .= ' loopstats';
1743
		}
1744
		if (!empty($config['ntpd']['peerstats'])) {
1745
			$ntpcfg .= ' peerstats';
1746
		}
1747
		$ntpcfg .= "\n";
1748
	}
1749
	$ntpcfg .= "statsdir {$statsdir}\n";
1750
	$ntpcfg .= 'logconfig =syncall +clockall';
1751
	if (!empty($config['ntpd']['logpeer'])) {
1752
		$ntpcfg .= ' +peerall';
1753
	}
1754
	if (!empty($config['ntpd']['logsys'])) {
1755
		$ntpcfg .= ' +sysall';
1756
	}
1757
	$ntpcfg .= "\n";
1758
	$ntpcfg .= "driftfile {$driftfile}\n";
1759

    
1760
	/* Default Access restrictions */
1761
	$ntpcfg .= 'restrict default';
1762
	if (empty($config['ntpd']['kod'])) { /*note: this one works backwards */
1763
		$ntpcfg .= ' kod limited';
1764
	}
1765
	if (empty($config['ntpd']['nomodify'])) { /*note: this one works backwards */
1766
		$ntpcfg .= ' nomodify';
1767
	}
1768
	if (!empty($config['ntpd']['noquery'])) {
1769
		$ntpcfg .= ' noquery';
1770
	}
1771
	if (empty($config['ntpd']['nopeer'])) { /*note: this one works backwards */
1772
		$ntpcfg .= ' nopeer';
1773
	}
1774
	if (empty($config['ntpd']['notrap'])) { /*note: this one works backwards */
1775
		$ntpcfg .= ' notrap';
1776
	}
1777
	if (!empty($config['ntpd']['noserve'])) {
1778
		$ntpcfg .= ' noserve';
1779
	}
1780
	$ntpcfg .= "\nrestrict -6 default";
1781
	if (empty($config['ntpd']['kod'])) { /*note: this one works backwards */
1782
		$ntpcfg .= ' kod limited';
1783
	}
1784
	if (empty($config['ntpd']['nomodify'])) { /*note: this one works backwards */
1785
		$ntpcfg .= ' nomodify';
1786
	}
1787
	if (!empty($config['ntpd']['noquery'])) {
1788
		$ntpcfg .= ' noquery';
1789
	}
1790
	if (empty($config['ntpd']['nopeer'])) { /*note: this one works backwards */
1791
		$ntpcfg .= ' nopeer';
1792
	}
1793
	if (!empty($config['ntpd']['noserve'])) {
1794
		$ntpcfg .= ' noserve';
1795
	}
1796
	if (empty($config['ntpd']['notrap'])) { /*note: this one works backwards */
1797
		$ntpcfg .= ' notrap';
1798
	}
1799
	/* Custom Access Restrictions */
1800
	if (is_array($config['ntpd']['restrictions']) && is_array($config['ntpd']['restrictions']['row'])) {
1801
		$networkacl = $config['ntpd']['restrictions']['row'];
1802
		foreach ($networkacl as $acl) {
1803
			$ntpcfg .= "\nrestrict ";
1804
			if (is_ipaddrv6($acl['acl_network'])) {
1805
				$ntpcfg .= "-6 {$acl['acl_network']} mask " . gen_subnet_mask_v6($acl['mask']) . " ";
1806
			} elseif (is_ipaddrv4($acl['acl_network'])) {
1807
				$ntpcfg .= "{$acl['acl_network']} mask " . gen_subnet_mask($acl['mask']) . " ";
1808
			} else {
1809
				continue;
1810
			}
1811
			if (!empty($acl['kod'])) {
1812
				$ntpcfg .= ' kod limited';
1813
			}
1814
			if (!empty($acl['nomodify'])) {
1815
				$ntpcfg .= ' nomodify';
1816
			}
1817
			if (!empty($acl['noquery'])) {
1818
				$ntpcfg .= ' noquery';
1819
			}
1820
			if (!empty($acl['nopeer'])) {
1821
				$ntpcfg .= ' nopeer';
1822
			}
1823
			if (!empty($acl['noserve'])) {
1824
				$ntpcfg .= ' noserve';
1825
			}
1826
			if (!empty($acl['notrap'])) {
1827
				$ntpcfg .= ' notrap';
1828
			}
1829
		}
1830
	}
1831
	$ntpcfg .= "\n";
1832
	/* End Custom Access Restrictions */
1833

    
1834
	/* A leapseconds file is really only useful if this clock is stratum 1 */
1835
	$ntpcfg .= "\n";
1836
	if (!empty($config['ntpd']['leapsec'])) {
1837
		$leapsec .= base64_decode($config['ntpd']['leapsec']);
1838
		file_put_contents('/var/db/leap-seconds', $leapsec);
1839
		$ntpcfg .= "leapfile /var/db/leap-seconds\n";
1840
	}
1841

    
1842

    
1843
	if (empty($config['ntpd']['interface'])) {
1844
		if (is_array($config['installedpackages']['openntpd']) && !empty($config['installedpackages']['openntpd']['config'][0]['interface'])) {
1845
			$interfaces = explode(",", $config['installedpackages']['openntpd']['config'][0]['interface']);
1846
		} else {
1847
			$interfaces = array();
1848
		}
1849
	} else {
1850
		$interfaces = explode(",", $config['ntpd']['interface']);
1851
	}
1852

    
1853
	if (is_array($interfaces) && count($interfaces)) {
1854
		$finterfaces = array();
1855
		$ntpcfg .= "interface ignore all\n";
1856
		foreach ($interfaces as $interface) {
1857
			$interface = get_real_interface($interface);
1858
			if (!empty($interface)) {
1859
				$finterfaces[] = $interface;
1860
			}
1861
		}
1862
		foreach ($finterfaces as $interface) {
1863
			$ntpcfg .= "interface listen {$interface}\n";
1864
		}
1865
	}
1866

    
1867
	/* open configuration for writing or bail */
1868
	if (!@file_put_contents("{$g['varetc_path']}/ntpd.conf", $ntpcfg)) {
1869
		log_error(sprintf(gettext("Could not open %s/ntpd.conf for writing"), $g['varetc_path']));
1870
		return;
1871
	}
1872

    
1873
	/* if ntpd is running, kill it */
1874
	while (isvalidpid("{$g['varrun_path']}/ntpd.pid")) {
1875
		killbypid("{$g['varrun_path']}/ntpd.pid");
1876
	}
1877
	@unlink("{$g['varrun_path']}/ntpd.pid");
1878

    
1879
	/* if /var/empty does not exist, create it */
1880
	if (!is_dir("/var/empty")) {
1881
		mkdir("/var/empty", 0775, true);
1882
	}
1883

    
1884
	/* start opentpd, set time now and use /var/etc/ntpd.conf */
1885
	mwexec("/usr/local/sbin/ntpd -g -c {$g['varetc_path']}/ntpd.conf -p {$g['varrun_path']}/ntpd.pid", false, true);
1886

    
1887
	// Note that we are starting up
1888
	log_error("NTPD is starting up.");
1889
	return;
1890
}
1891

    
1892
function system_halt() {
1893
	global $g;
1894

    
1895
	system_reboot_cleanup();
1896

    
1897
	mwexec("/usr/bin/nohup /etc/rc.halt > /dev/null 2>&1 &");
1898
}
1899

    
1900
function system_reboot() {
1901
	global $g;
1902

    
1903
	system_reboot_cleanup();
1904

    
1905
	mwexec("nohup /etc/rc.reboot > /dev/null 2>&1 &");
1906
}
1907

    
1908
function system_reboot_sync() {
1909
	global $g;
1910

    
1911
	system_reboot_cleanup();
1912

    
1913
	mwexec("/etc/rc.reboot > /dev/null 2>&1");
1914
}
1915

    
1916
function system_reboot_cleanup() {
1917
	global $config, $cpzone;
1918

    
1919
	mwexec("/usr/local/bin/beep.sh stop");
1920
	require_once("captiveportal.inc");
1921
	if (is_array($config['captiveportal'])) {
1922
		foreach ($config['captiveportal'] as $cpzone=>$cp) {
1923
			captiveportal_radius_stop_all();
1924
			captiveportal_send_server_accounting(true);
1925
		}
1926
	}
1927
	require_once("voucher.inc");
1928
	voucher_save_db_to_config();
1929
	require_once("pkg-utils.inc");
1930
	stop_packages();
1931
}
1932

    
1933
function system_do_shell_commands($early = 0) {
1934
	global $config, $g;
1935
	if (isset($config['system']['developerspew'])) {
1936
		$mt = microtime();
1937
		echo "system_do_shell_commands() being called $mt\n";
1938
	}
1939

    
1940
	if ($early) {
1941
		$cmdn = "earlyshellcmd";
1942
	} else {
1943
		$cmdn = "shellcmd";
1944
	}
1945

    
1946
	if (is_array($config['system'][$cmdn])) {
1947

    
1948
		/* *cmd is an array, loop through */
1949
		foreach ($config['system'][$cmdn] as $cmd) {
1950
			exec($cmd);
1951
		}
1952

    
1953
	} elseif ($config['system'][$cmdn] <> "") {
1954

    
1955
		/* execute single item */
1956
		exec($config['system'][$cmdn]);
1957

    
1958
	}
1959
}
1960

    
1961
function system_dmesg_save() {
1962
	global $g;
1963
	if (isset($config['system']['developerspew'])) {
1964
		$mt = microtime();
1965
		echo "system_dmesg_save() being called $mt\n";
1966
	}
1967

    
1968
	$dmesg = "";
1969
	$_gb = exec("/sbin/dmesg", $dmesg);
1970

    
1971
	/* find last copyright line (output from previous boots may be present) */
1972
	$lastcpline = 0;
1973

    
1974
	for ($i = 0; $i < count($dmesg); $i++) {
1975
		if (strstr($dmesg[$i], "Copyright (c) 1992-")) {
1976
			$lastcpline = $i;
1977
		}
1978
	}
1979

    
1980
	$fd = fopen("{$g['varlog_path']}/dmesg.boot", "w");
1981
	if (!$fd) {
1982
		printf(gettext("Error: cannot open dmesg.boot in system_dmesg_save().%s"), "\n");
1983
		return 1;
1984
	}
1985

    
1986
	for ($i = $lastcpline; $i < count($dmesg); $i++) {
1987
		fwrite($fd, $dmesg[$i] . "\n");
1988
	}
1989

    
1990
	fclose($fd);
1991
	unset($dmesg);
1992

    
1993
	return 0;
1994
}
1995

    
1996
function system_set_harddisk_standby() {
1997
	global $g, $config;
1998

    
1999
	if (isset($config['system']['developerspew'])) {
2000
		$mt = microtime();
2001
		echo "system_set_harddisk_standby() being called $mt\n";
2002
	}
2003

    
2004
	if (isset($config['system']['harddiskstandby'])) {
2005
		if (platform_booting()) {
2006
			echo gettext('Setting hard disk standby... ');
2007
		}
2008

    
2009
		$standby = $config['system']['harddiskstandby'];
2010
		// Check for a numeric value
2011
		if (is_numeric($standby)) {
2012
			// Get only suitable candidates for standby; using get_smart_drive_list()
2013
			// from utils.inc to get the list of drives.
2014
			$harddisks = get_smart_drive_list();
2015

    
2016
			// Since get_smart_drive_list() only matches ad|da|ada; lets put the check below
2017
			// just in case of some weird pfSense platform installs.
2018
			if (count($harddisks) > 0) {
2019
				// Iterate disks and run the camcontrol command for each
2020
				foreach ($harddisks as $harddisk) {
2021
					mwexec("/sbin/camcontrol standby {$harddisk} -t {$standby}");
2022
				}
2023
				if (platform_booting()) {
2024
					echo gettext("done.") . "\n";
2025
				}
2026
			} else if (platform_booting()) {
2027
				echo gettext("failed!") . "\n";
2028
			}
2029
		} else if (platform_booting()) {
2030
			echo gettext("failed!") . "\n";
2031
		}
2032
	}
2033
}
2034

    
2035
function system_setup_sysctl() {
2036
	global $config;
2037
	if (isset($config['system']['developerspew'])) {
2038
		$mt = microtime();
2039
		echo "system_setup_sysctl() being called $mt\n";
2040
	}
2041

    
2042
	activate_sysctls();
2043

    
2044
	if (isset($config['system']['sharednet'])) {
2045
		system_disable_arp_wrong_if();
2046
	}
2047
}
2048

    
2049
function system_disable_arp_wrong_if() {
2050
	global $config;
2051
	if (isset($config['system']['developerspew'])) {
2052
		$mt = microtime();
2053
		echo "system_disable_arp_wrong_if() being called $mt\n";
2054
	}
2055
	set_sysctl(array(
2056
		"net.link.ether.inet.log_arp_wrong_iface" => "0",
2057
		"net.link.ether.inet.log_arp_movements" => "0"
2058
	));
2059
}
2060

    
2061
function system_enable_arp_wrong_if() {
2062
	global $config;
2063
	if (isset($config['system']['developerspew'])) {
2064
		$mt = microtime();
2065
		echo "system_enable_arp_wrong_if() being called $mt\n";
2066
	}
2067
	set_sysctl(array(
2068
		"net.link.ether.inet.log_arp_wrong_iface" => "1",
2069
		"net.link.ether.inet.log_arp_movements" => "1"
2070
	));
2071
}
2072

    
2073
function enable_watchdog() {
2074
	global $config;
2075
	return;
2076
	$install_watchdog = false;
2077
	$supported_watchdogs = array("Geode");
2078
	$file = file_get_contents("/var/log/dmesg.boot");
2079
	foreach ($supported_watchdogs as $sd) {
2080
		if (stristr($file, "Geode")) {
2081
			$install_watchdog = true;
2082
		}
2083
	}
2084
	if ($install_watchdog == true) {
2085
		if (is_process_running("watchdogd")) {
2086
			mwexec("/usr/bin/killall watchdogd", true);
2087
		}
2088
		exec("/usr/sbin/watchdogd");
2089
	}
2090
}
2091

    
2092
function system_check_reset_button() {
2093
	global $g;
2094

    
2095
	$specplatform = system_identify_specific_platform();
2096

    
2097
	switch ($specplatform['name']) {
2098
		case 'alix':
2099
		case 'wrap':
2100
		case 'FW7541':
2101
		case 'APU':
2102
		case 'RCC-VE':
2103
		case 'RCC':
2104
		case 'RCC-DFF':
2105
			break;
2106
		default:
2107
			return 0;
2108
	}
2109

    
2110
	$retval = mwexec("/usr/local/sbin/" . $specplatform['name'] . "resetbtn");
2111

    
2112
	if ($retval == 99) {
2113
		/* user has pressed reset button for 2 seconds -
2114
		   reset to factory defaults */
2115
		echo <<<EOD
2116

    
2117
***********************************************************************
2118
* Reset button pressed - resetting configuration to factory defaults. *
2119
* All additional packages installed will be removed                   *
2120
* The system will reboot after this completes.                        *
2121
***********************************************************************
2122

    
2123

    
2124
EOD;
2125

    
2126
		reset_factory_defaults();
2127
		system_reboot_sync();
2128
		exit(0);
2129
	}
2130

    
2131
	return 0;
2132
}
2133

    
2134
function system_get_serial() {
2135
	unset($output);
2136
	$_gb = exec('/bin/kenv smbios.system.serial 2>/dev/null', $output);
2137
	$serial = $output[0];
2138

    
2139
	$vm_guest = get_single_sysctl('kern.vm_guest');
2140

    
2141
	if (strlen($serial) >= 10 && strlen($serial) <= 16 &&
2142
	    $vm_guest == 'none') {
2143
		return $serial;
2144
	}
2145

    
2146
	return get_single_sysctl('kern.hostuuid');
2147
}
2148

    
2149
/*
2150
 * attempt to identify the specific platform (for embedded systems)
2151
 * Returns an array with two elements:
2152
 * name => platform string (e.g. 'wrap', 'alix' etc.)
2153
 * descr => human-readable description (e.g. "PC Engines WRAP")
2154
 */
2155
function system_identify_specific_platform() {
2156
	global $g;
2157

    
2158
	$hw_model = get_single_sysctl('hw.model');
2159

    
2160
	/* Try to guess from smbios strings */
2161
	unset($product);
2162
	unset($maker);
2163
	$_gb = exec('/bin/kenv smbios.system.product 2>/dev/null', $product);
2164
	$_gb = exec('/bin/kenv smbios.system.maker 2>/dev/null', $maker);
2165
	switch ($product[0]) {
2166
		case 'FW7541':
2167
			return (array('name' => 'FW7541', 'descr' => 'Netgate FW7541'));
2168
			break;
2169
		case 'APU':
2170
			return (array('name' => 'APU', 'descr' => 'Netgate APU'));
2171
			break;
2172
		case 'RCC-VE':
2173
			$result = array();
2174
			$result['name'] = 'RCC-VE';
2175

    
2176
			/* Detect specific models */
2177
			if (!function_exists('does_interface_exist')) {
2178
				require_once("interfaces.inc");
2179
			}
2180
			if (!does_interface_exist('igb4')) {
2181
				$result['model'] = 'SG-2440';
2182
			} elseif (strpos($hw_model, "C2558") !== false) {
2183
				$result['model'] = 'SG-4860';
2184
			} elseif (strpos($hw_model, "C2758") !== false) {
2185
				$result['model'] = 'SG-8860';
2186
			} else {
2187
				$result['model'] = 'RCC-VE';
2188
			}
2189
			$result['descr'] = 'Netgate ' . $result['model'];
2190
			return $result;
2191
			break;
2192
		case 'DFFv2':
2193
			return (array('name' => 'RCC-DFF', 'descr' => 'Netgate RCC-DFF'));
2194
			break;
2195
		case 'RCC':
2196
			return (array('name' => 'RCC', 'descr' => 'Netgate XG-2758'));
2197
			break;
2198
		case 'SYS-5018A-FTN4':
2199
		case 'A1SAi':
2200
			return (array('name' => 'C2758', 'descr' => 'Super Micro C2758'));
2201
			break;
2202
		case 'SYS-5018D-FN4T':
2203
			return (array('name' => 'XG-1540', 'descr' => 'Super Micro XG-1540'));
2204
			break;
2205
		case 'Virtual Machine':
2206
			if ($maker[0] == "Microsoft Corporation") {
2207
				return (array('name' => 'Hyper-V', 'descr' => 'Hyper-V Virtual Machine'));
2208
			}
2209
			break;
2210
	}
2211

    
2212
	/* the rest of the code only deals with 'embedded' platforms */
2213
	if ($g['platform'] != 'nanobsd') {
2214
		return array('name' => $g['platform'], 'descr' => $g['platform']);
2215
	}
2216

    
2217
	if (strpos($hw_model, "PC Engines WRAP") !== false) {
2218
		return array('name' => 'wrap', 'descr' => gettext('PC Engines WRAP'));
2219
	}
2220

    
2221
	if (strpos($hw_model, "PC Engines ALIX") !== false) {
2222
		return array('name' => 'alix', 'descr' => gettext('PC Engines ALIX'));
2223
	}
2224

    
2225
	if (preg_match("/Soekris net45../", $hw_model, $matches)) {
2226
		return array('name' => 'net45xx', 'descr' => $matches[0]);
2227
	}
2228

    
2229
	if (preg_match("/Soekris net48../", $hw_model, $matches)) {
2230
		return array('name' => 'net48xx', 'descr' => $matches[0]);
2231
	}
2232

    
2233
	if (preg_match("/Soekris net55../", $hw_model, $matches)) {
2234
		return array('name' => 'net55xx', 'descr' => $matches[0]);
2235
	}
2236

    
2237
	unset($hw_model);
2238

    
2239
	$dmesg_boot = system_get_dmesg_boot();
2240
	if (strpos($dmesg_boot, "PC Engines ALIX") !== false) {
2241
		return array('name' => 'alix', 'descr' => gettext('PC Engines ALIX'));
2242
	}
2243
	unset($dmesg_boot);
2244

    
2245
	/* unknown embedded platform */
2246
	return array('name' => 'embedded', 'descr' => gettext('embedded (unknown)'));
2247
}
2248

    
2249
function system_get_dmesg_boot() {
2250
	global $g;
2251

    
2252
	return file_get_contents("{$g['varlog_path']}/dmesg.boot");
2253
}
2254

    
2255
?>
(52-52/65)