Project

General

Profile

Download (66.6 KB) Statistics
| Branch: | Tag: | Revision:
1
<?php
2
/* $Id$ */
3
/*
4
	system.inc
5
	part of m0n0wall (http://m0n0.ch/wall)
6

    
7
	Copyright (C) 2003-2004 Manuel Kasper <mk@neon1.net>.
8
	All rights reserved.
9

    
10
	Redistribution and use in source and binary forms, with or without
11
	modification, are permitted provided that the following conditions are met:
12

    
13
	1. Redistributions of source code must retain the above copyright notice,
14
	   this list of conditions and the following disclaimer.
15

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

    
20
	THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
21
	INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
22
	AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
23
	AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY,
24
	OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25
	SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26
	INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27
	CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28
	ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29
	POSSIBILITY OF SUCH DAMAGE.
30
*/
31

    
32
/*
33
	pfSense_BUILDER_BINARIES:	/usr/sbin/powerd	/usr/bin/killall	/sbin/route
34
	pfSense_BUILDER_BINARIES:	/bin/hostname	/bin/ls	/usr/sbin/syslogd	
35
	pfSense_BUILDER_BINARIES:	/usr/sbin/pccardd	/usr/local/sbin/lighttpd	/bin/chmod 	/bin/mkdir
36
	pfSense_BUILDER_BINARIES:	/usr/bin/tar		/usr/local/sbin/ntpd	/usr/local/sbin/ntpdate
37
	pfSense_BUILDER_BINARIES:	/usr/bin/nohup	/sbin/dmesg	/usr/local/sbin/atareinit	/sbin/kldload
38
	pfSense_BUILDER_BINARIES:	/usr/local/sbin/filterdns
39
	pfSense_MODULE:	utils
40
*/
41

    
42
function activate_powerd() {
43
	global $config, $g;
44
	if ($g['platform'] == 'jail')
45
		return;
46
	if(is_process_running("powerd"))
47
		exec("/usr/bin/killall powerd");
48
	if(isset($config['system']['powerd_enable'])) {
49
		if ($g["platform"] == "nanobsd")
50
			exec("/sbin/kldload cpufreq");
51

    
52
		$ac_mode = "hadp";
53
		if (!empty($config['system']['powerd_ac_mode']))
54
			$ac_mode = $config['system']['powerd_ac_mode'];
55

    
56
		$battery_mode = "hadp";
57
		if (!empty($config['system']['powerd_battery_mode']))
58
			$battery_mode = $config['system']['powerd_battery_mode'];
59

    
60
		$normal_mode = "hadp";
61
		if (!empty($config['system']['powerd_normal_mode']))
62
			$normal_mode = $config['system']['powerd_normal_mode'];
63

    
64
		mwexec("/usr/sbin/powerd -b $battery_mode -a $ac_mode -n $normal_mode");
65
	}
66
}
67

    
68
function get_default_sysctl_value($id) {
69
	global $sysctls;
70

    
71
	if (isset($sysctls[$id]))
72
		return $sysctls[$id];
73
}
74

    
75
function get_sysctl_descr($sysctl) {
76
	unset($output);
77
	$_gb = exec("/sbin/sysctl -nd {$sysctl}", $output);
78

    
79
	return $output[0];
80
}
81

    
82
function system_get_sysctls() {
83
	global $config, $sysctls;
84

    
85
	$disp_sysctl = array();
86
	$disp_cache = array();
87
	if (is_array($config['sysctl']) && is_array($config['sysctl']['item'])) {
88
		foreach($config['sysctl']['item'] as $id => $tunable) {
89
			if ($tunable['value'] == "default")
90
				$value = get_default_sysctl_value($tunable['tunable']);
91
			else
92
				$value = $tunable['value'];
93

    
94
			$disp_sysctl[$id] = $tunable;
95
			$disp_sysctl[$id]['modified'] = true;
96
			$disp_cache[$tunable['tunable']] = 'set';
97
		}
98
	}
99

    
100
	foreach ($sysctls as $sysctl => $value) {
101
		if (isset($disp_cache[$sysctl]))
102
			continue;
103

    
104
		$disp_sysctl[$sysctl] = array('tunable' => $sysctl, 'value' => $value, 'descr' => get_sysctl_descr($sysctl));
105
	}
106
	unset($disp_cache);
107
	return $disp_sysctl;
108
}
109

    
110
function activate_sysctls() {
111
	global $config, $g, $sysctls;
112

    
113
	if ($g['platform'] == 'jail')
114
		return;
115

    
116
	if (is_array($config['sysctl']) && is_array($config['sysctl']['item'])) {
117
		foreach($config['sysctl']['item'] as $tunable) {
118
			if($tunable['value'] == "default")
119
				$value = get_default_sysctl_value($tunable['tunable']);
120
			else
121
				$value = $tunable['value'];
122

    
123
			$sysctls[$tunable['tunable']] = $value;
124
		}
125
	}
126

    
127
	set_sysctl($sysctls);
128
}
129

    
130
function system_resolvconf_generate($dynupdate = false) {
131
	global $config, $g;
132

    
133
	if(isset($config['system']['developerspew'])) {
134
		$mt = microtime();
135
		echo "system_resolvconf_generate() being called $mt\n";
136
	}
137

    
138
	$syscfg = $config['system'];
139

    
140
	if (((isset($config['dnsmasq']['enable']) && (!isset($config['dnsmasq']['port']) || $config['dnsmasq']['port'] == "53") && (empty($config['dnsmasq']['interface']) || in_array("lo0", explode(",", $config['dnsmasq']['interface']))))
141
		|| (isset($config['unbound']['enable'])) && (!isset($config['unbound']['port']) || $config['unbound']['port'] == "53") && (empty($config['unbound']['active_interface']) || in_array("lo0", explode(",", $config['unbound']['active_interface'])) || in_array("all", explode(",", $config['unbound']['active_interface']), true)))
142
		&& !isset($config['system']['dnslocalhost']))
143
		$resolvconf .= "nameserver 127.0.0.1\n";
144

    
145
	if (isset($syscfg['dnsallowoverride'])) {
146
		/* get dynamically assigned DNS servers (if any) */
147
		$ns = array_unique(get_searchdomains());
148
		foreach($ns as $searchserver) {
149
			if($searchserver)
150
				$resolvconf .= "search {$searchserver}\n";
151
		}
152
		$ns = array_unique(get_nameservers());
153
		foreach($ns as $nameserver) {
154
			if($nameserver)
155
				$resolvconf .= "nameserver $nameserver\n";
156
		}
157
	} else {
158
		// Do not create blank search/domain lines, it can break tools like dig.
159
		if($syscfg['domain'])
160
			$resolvconf .= "search {$syscfg['domain']}\n";
161
	}
162
	if (is_array($syscfg['dnsserver'])) {
163
		foreach ($syscfg['dnsserver'] as $ns) {
164
			if ($ns)
165
				$resolvconf .= "nameserver $ns\n";
166
		}
167
	}
168

    
169
	// Add EDNS support
170
	if (isset($config['unbound']['enable']) && isset($config['unbound']['edns']))
171
		$resolvconf .= "options edns0\n";
172

    
173
	$dnslock = lock('resolvconf', LOCK_EX);
174

    
175
	$fd = fopen("{$g['varetc_path']}/resolv.conf", "w");
176
	if (!$fd) {
177
		printf("Error: cannot open resolv.conf in system_resolvconf_generate().\n");
178
		unlock($dnslock);
179
		return 1;
180
	}
181

    
182
	fwrite($fd, $resolvconf);
183
	fclose($fd);
184

    
185
	// Prevent resolvconf(8) from rewriting our resolv.conf
186
	$fd = fopen("{$g['varetc_path']}/resolvconf.conf", "w");
187
	if (!$fd) {
188
		printf("Error: cannot open resolvconf.conf in system_resolvconf_generate().\n");
189
		return 1;
190
	}
191
	fwrite($fd, "resolv_conf=\"/dev/null\"\n");
192
	fclose($fd);
193

    
194
	if (!platform_booting()) {
195
		/* restart dhcpd (nameservers may have changed) */
196
		if (!$dynupdate)
197
			services_dhcpd_configure();
198
	}
199

    
200
	/* setup static routes for DNS servers. */
201
	for ($dnscounter=1; $dnscounter<5; $dnscounter++) {
202
		/* setup static routes for dns servers */
203
		$dnsgw = "dns{$dnscounter}gw";
204
		if (isset($config['system'][$dnsgw])) {
205
			$gwname = $config['system'][$dnsgw];
206
			if (($gwname <> "") && ($gwname <> "none")) {
207
				$gatewayip = lookup_gateway_ip_by_name($gwname);
208
				if (is_ipaddrv4($gatewayip)) {
209
					/* dns server array starts at 0 */
210
					$dnscountermo = $dnscounter - 1;
211
					mwexec("/sbin/route change -host " . $syscfg['dnsserver'][$dnscountermo] . " {$gatewayip}");
212
					if (isset($config['system']['route-debug'])) {
213
						$mt = microtime();
214
						log_error("ROUTING debug: $mt - route change -host {$syscfg['dnsserver'][$dnscountermo]} $gatewayip ");
215
					}
216
				}
217
				if (is_ipaddrv6($gatewayip)) {
218
					/* dns server array starts at 0 */
219
					$dnscountermo = $dnscounter - 1;
220
					mwexec("/sbin/route change -host -inet6 " . $syscfg['dnsserver'][$dnscountermo] . " {$gatewayip}");
221
					if (isset($config['system']['route-debug'])) {
222
						$mt = microtime();
223
						log_error("ROUTING debug: $mt - route change -host -inet6 {$syscfg['dnsserver'][$dnscountermo]} $gatewayip ");
224
					}					
225
				}
226
			}
227
		}
228
	}
229

    
230
	unlock($dnslock);
231

    
232
	return 0;
233
}
234

    
235
function get_searchdomains() {
236
	global $config, $g;
237

    
238
	$master_list = array();
239
	
240
	// Read in dhclient nameservers
241
	$search_list = glob("/var/etc/searchdomain_*");
242
	if (is_array($search_list)) {
243
		foreach($search_list as $fdns) {
244
			$contents = file($fdns, FILE_IGNORE_NEW_LINES | FILE_SKIP_EMPTY_LINES);
245
			if (!is_array($contents))
246
				continue;
247
			foreach ($contents as $dns) {
248
				if(is_hostname($dns)) 
249
					$master_list[] = $dns;
250
			}
251
		}
252
	}
253

    
254
	return $master_list;
255
}
256

    
257
function get_nameservers() {
258
	global $config, $g;
259
	$master_list = array();
260
	
261
	// Read in dhclient nameservers
262
	$dns_lists = glob("/var/etc/nameserver_*");
263
	if (is_array($dns_lists)) {
264
		foreach($dns_lists as $fdns) {
265
			$contents = file($fdns, FILE_IGNORE_NEW_LINES | FILE_SKIP_EMPTY_LINES);
266
			if (!is_array($contents))
267
				continue;
268
			foreach ($contents as $dns) {
269
				if(is_ipaddr($dns)) 
270
					$master_list[] = $dns;
271
			}
272
		}
273
	}
274

    
275
	// Read in any extra nameservers
276
	if(file_exists("/var/etc/nameservers.conf")) {
277
		$dns_s = file("/var/etc/nameservers.conf", FILE_IGNORE_NEW_LINES | FILE_SKIP_EMPTY_LINES);
278
		if(is_array($dns_s)) {
279
			foreach($dns_s as $dns)
280
				if (is_ipaddr($dns))
281
					$master_list[] = $dns;
282
		}
283
	}
284

    
285
	return $master_list;
286
}
287

    
288
function system_hosts_generate() {
289
	global $config, $g;
290
	if (isset($config['system']['developerspew'])) {
291
		$mt = microtime();
292
		echo "system_hosts_generate() being called $mt\n";
293
	}
294

    
295
	$syscfg = $config['system'];
296
	if (isset($config['unbound']) && isset($config['unbound']['enable']))
297
		$dnsmasqcfg = $config['unbound'];
298
	else
299
		$dnsmasqcfg = $config['dnsmasq'];
300

    
301
	$hosts =  "127.0.0.1	localhost localhost.{$syscfg['domain']}\n";
302
	$hosts .= "::1		localhost localhost.{$syscfg['domain']}\n";
303
	$lhosts = "";
304
	$dhosts = "";
305

    
306
	if ($config['interfaces']['lan']) {
307
		$cfgip = get_interface_ip("lan");
308
		if (is_ipaddr($cfgip))
309
			$hosts .= "{$cfgip}	{$syscfg['hostname']}.{$syscfg['domain']} {$syscfg['hostname']}\n";
310
		$cfgipv6 = get_interface_ipv6("lan");
311
		if (is_ipaddrv6($cfgipv6))
312
			$hosts .= "{$cfgipv6}	{$syscfg['hostname']}.{$syscfg['domain']} {$syscfg['hostname']}\n";
313
	} else {
314
		$sysiflist = get_configured_interface_list();
315
		$hosts_if_found = false;
316
		foreach ($sysiflist as $sysif) {
317
			if (!interface_has_gateway($sysif)) {
318
				$cfgip = get_interface_ip($sysif);
319
				if (is_ipaddr($cfgip)) {
320
					$hosts .= "{$cfgip}	{$syscfg['hostname']}.{$syscfg['domain']} {$syscfg['hostname']}\n";
321
					$hosts_if_found = true;
322
				}
323
				$cfgipv6 = get_interface_ipv6($sysif);
324
				if (is_ipaddrv6($cfgipv6)) {
325
					$hosts .= "{$cfgipv6}	{$syscfg['hostname']}.{$syscfg['domain']} {$syscfg['hostname']}\n";
326
					$hosts_if_found = true;
327
				}
328
				if ($hosts_if_found == true)
329
					break;
330
			}
331
		}
332
	}
333

    
334
	if (isset($dnsmasqcfg['enable'])) {
335
		if (!is_array($dnsmasqcfg['hosts']))
336
			$dnsmasqcfg['hosts'] = array();
337

    
338
		foreach ($dnsmasqcfg['hosts'] as $host) {
339
			if ($host['host'])
340
				$lhosts .= "{$host['ip']}	{$host['host']}.{$host['domain']} {$host['host']}\n";
341
			else
342
				$lhosts .= "{$host['ip']}	{$host['domain']}\n";
343
			if (!is_array($host['aliases']) || !is_array($host['aliases']['item']))
344
				continue;
345
			foreach ($host['aliases']['item'] as $alias) {
346
				if ($alias['host'])
347
					$lhosts .= "{$host['ip']}	{$alias['host']}.{$alias['domain']} {$alias['host']}\n";
348
				else
349
					$lhosts .= "{$host['ip']}	{$alias['domain']}\n";
350
			}
351
		}
352
		if (isset($dnsmasqcfg['regdhcpstatic']) && is_array($config['dhcpd'])) {
353
			foreach ($config['dhcpd'] as $dhcpif => $dhcpifconf)
354
				if(is_array($dhcpifconf['staticmap']) && isset($dhcpifconf['enable']))
355
						foreach ($dhcpifconf['staticmap'] as $host)
356
							if ($host['ipaddr'] && $host['hostname'] && $host['domain'])
357
								$dhosts .= "{$host['ipaddr']}	{$host['hostname']}.{$host['domain']} {$host['hostname']}\n";
358
							else if ($host['ipaddr'] && $host['hostname'] && $dhcpifconf['domain'])
359
								$dhosts .= "{$host['ipaddr']}	{$host['hostname']}.{$dhcpifconf['domain']} {$host['hostname']}\n";
360
							else if ($host['ipaddr'] && $host['hostname'])
361
								$dhosts .= "{$host['ipaddr']}	{$host['hostname']}.{$syscfg['domain']} {$host['hostname']}\n";
362
		}
363
		if (isset($dnsmasqcfg['regdhcpstatic']) && is_array($config['dhcpdv6'])) {
364
			foreach ($config['dhcpdv6'] as $dhcpif => $dhcpifconf)
365
				if(is_array($dhcpifconf['staticmap']) && isset($dhcpifconf['enable']))
366
						foreach ($dhcpifconf['staticmap'] as $host)
367
							if ($host['ipaddrv6'] && $host['hostname'] && $host['domain'])
368
								$dhosts .= "{$host['ipaddrv6']}	{$host['hostname']}.{$host['domain']} {$host['hostname']}\n";
369
							else if ($host['ipaddrv6'] && $host['hostname'] && $dhcpifconf['domain'])
370
								$dhosts .= "{$host['ipaddrv6']}	{$host['hostname']}.{$dhcpifconf['domain']} {$host['hostname']}\n";
371
							else if ($host['ipaddrv6'] && $host['hostname'])
372
								$dhosts .= "{$host['ipaddrv6']}	{$host['hostname']}.{$syscfg['domain']} {$host['hostname']}\n";
373
		}
374

    
375
		if (isset($dnsmasqcfg['dhcpfirst']))
376
			$hosts .= $dhosts . $lhosts;
377
		else
378
			$hosts .= $lhosts . $dhosts;
379
	}
380

    
381
	/*
382
	 * Do not remove this because dhcpleases monitors with kqueue it needs to be 
383
	 * killed before writing to hosts files.
384
	 */
385
	if (file_exists("{$g['varrun_path']}/dhcpleases.pid")) {
386
		sigkillbypid("{$g['varrun_path']}/dhcpleases.pid", "TERM");
387
		@unlink("{$g['varrun_path']}/dhcpleases.pid");
388
	}
389
	$fd = fopen("{$g['varetc_path']}/hosts", "w");
390
	if (!$fd) {
391
		log_error("Error: cannot open hosts file in system_hosts_generate().\n");
392
		return 1;
393
	}
394
	fwrite($fd, $hosts);
395
	fclose($fd);
396

    
397
	if (isset($config['unbound']['enable'])) {
398
		require_once("unbound.inc");
399
		unbound_hosts_generate();
400
	}
401

    
402
	return 0;
403
}
404

    
405
function system_dhcpleases_configure() {
406
	global $config, $g;
407
	
408
	if ($g['platform'] == 'jail')
409
		return;
410
	/* Start the monitoring process for dynamic dhcpclients. */
411
	if ((isset($config['dnsmasq']['enable']) && isset($config['dnsmasq']['regdhcp'])) 
412
		|| (isset($config['unbound']['enable']) && isset($config['unbound']['regdhcp']))) {
413
		/* Make sure we do not error out */
414
		mwexec("/bin/mkdir -p {$g['dhcpd_chroot_path']}/var/db");
415
		if (!file_exists("{$g['dhcpd_chroot_path']}/var/db/dhcpd.leases"))
416
			@touch("{$g['dhcpd_chroot_path']}/var/db/dhcpd.leases");
417

    
418
		if (isset($config['unbound']['enable'])) {
419
			$dns_pid = "unbound.pid";
420
			$unbound_conf = "-u {$g['unbound_chroot_path']}/dhcpleases_entries.conf";
421
		} else {
422
			$dns_pid = "dnsmasq.pid";
423
			$unbound_conf = "";
424
		}
425

    
426
		$pidfile = "{$g['varrun_path']}/dhcpleases.pid";
427
		if (isvalidpid($pidfile)) {
428
			/* Make sure dhcpleases is using correct unbound or dnsmasq */
429
			$_gb = exec("/bin/pgrep -F {$pidfile} -f {$dns_pid}", $output, $retval);
430
			if (intval($retval) == 0) {
431
				sigkillbypid($pidfile, "HUP");
432
				return;
433
			} else
434
				sigkillbypid($pidfile, "TERM");
435
		}
436

    
437
		/* To ensure we do not start multiple instances of dhcpleases, perform some clean-up first. */
438
		if (is_process_running("dhcpleases"))
439
			sigkillbyname('dhcpleases', "TERM");
440
		@unlink($pidfile);
441
		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");
442
	} else {
443
		sigkillbypid($pidfile, "TERM");
444
		@unlink($pidfile);
445
	}
446
}
447

    
448
function system_hostname_configure() {
449
	global $config, $g;
450
	if(isset($config['system']['developerspew'])) {
451
		$mt = microtime();
452
		echo "system_hostname_configure() being called $mt\n";
453
	}
454

    
455
	$syscfg = $config['system'];
456

    
457
	/* set hostname */
458
	$status = mwexec("/bin/hostname " .
459
		escapeshellarg("{$syscfg['hostname']}.{$syscfg['domain']}"));
460

    
461
    /* Setup host GUID ID.  This is used by ZFS. */
462
	mwexec("/etc/rc.d/hostid start");
463

    
464
	return $status;
465
}
466

    
467
function system_routing_configure($interface = "") {
468
	global $config, $g;
469
	if ($g['platform'] == 'jail')
470
		return;
471
	if(isset($config['system']['developerspew'])) {
472
		$mt = microtime();
473
		echo "system_routing_configure() being called $mt\n";
474
	}
475

    
476
	$gatewayip = "";
477
	$interfacegw = "";
478
	$gatewayipv6 = "";
479
	$interfacegwv6 = "";
480
	$foundgw = false;
481
	$foundgwv6 = false;
482
	/* tack on all the hard defined gateways as well */
483
	if (is_array($config['gateways']['gateway_item'])) {
484
		array_map('unlink', glob("{$g['tmp_path']}/*_defaultgw{,v6}", GLOB_BRACE));
485
		foreach	($config['gateways']['gateway_item'] as $gateway) {
486
			if (isset($gateway['defaultgw'])) {
487
				if ($foundgw == false && ($gateway['ipprotocol'] != "inet6" && (is_ipaddrv4($gateway['gateway']) || $gateway['gateway'] == "dynamic"))) {
488
					if(strpos($gateway['gateway'], ":"))
489
						continue;
490
					if ($gateway['gateway'] == "dynamic")
491
						$gateway['gateway'] = get_interface_gateway($gateway['interface']);
492
					$gatewayip = $gateway['gateway'];
493
					$interfacegw = $gateway['interface'];
494
					if (!empty($gateway['interface'])) {
495
						$defaultif = get_real_interface($gateway['interface']);
496
						if ($defaultif)
497
							@file_put_contents("{$g['tmp_path']}/{$defaultif}_defaultgw", $gateway['gateway']);
498
					}
499
					$foundgw = true;
500
				} else if ($foundgwv6 == false && ($gateway['ipprotocol'] == "inet6" && (is_ipaddrv6($gateway['gateway']) || $gateway['gateway'] == "dynamic"))) {
501
					if ($gateway['gateway'] == "dynamic")
502
						$gateway['gateway'] = get_interface_gateway_v6($gateway['interface']);
503
					$gatewayipv6 = $gateway['gateway'];
504
					$interfacegwv6 = $gateway['interface'];
505
					if (!empty($gateway['interface'])) {
506
						$defaultifv6 = get_real_interface($gateway['interface']);
507
						if ($defaultifv6)
508
							@file_put_contents("{$g['tmp_path']}/{$defaultifv6}_defaultgwv6", $gateway['gateway']);
509
					}
510
					$foundgwv6 = true;
511
				}
512
			}
513
			if ($foundgw === true && $foundgwv6 === true)
514
				break;
515
		}
516
	}
517
	if ($foundgw == false) {
518
		$defaultif = get_real_interface("wan");
519
		$interfacegw = "wan";
520
		$gatewayip = get_interface_gateway("wan");
521
		@file_put_contents("{$g['tmp_path']}/{$defaultif}_defaultgw", $gatewayip);
522
	}	
523
	if ($foundgwv6 == false) {
524
		$defaultifv6 = get_real_interface("wan");
525
		$interfacegwv6 = "wan";
526
		$gatewayipv6 = get_interface_gateway_v6("wan");
527
		@file_put_contents("{$g['tmp_path']}/{$defaultifv6}_defaultgwv6", $gatewayipv6);
528
	}
529
	$dont_add_route = false;
530
	/* if OLSRD is enabled, allow WAN to house DHCP. */
531
	if (is_array($config['installedpackages']['olsrd'])) {
532
		foreach($config['installedpackages']['olsrd']['config'] as $olsrd) {
533
			if(($olsrd['enabledyngw'] == "on") && ($olsrd['enable'] == "on")) {
534
				$dont_add_route = true;
535
				log_error(sprintf(gettext("Not adding default route because OLSR dynamic gateway is enabled.")));
536
				break;
537
			}
538
		}
539
	}
540

    
541
	if ($dont_add_route == false ) {
542
		if (!empty($interface) && $interface != $interfacegw)
543
			;
544
		else if (is_ipaddrv4($gatewayip)) {
545
			log_error("ROUTING: setting default route to $gatewayip");
546
			mwexec("/sbin/route change -inet default " . escapeshellarg($gatewayip));
547
		}
548

    
549
		if (!empty($interface) && $interface != $interfacegwv6)
550
			;
551
		else if (is_ipaddrv6($gatewayipv6)) {
552
			$ifscope = "";
553
			if (is_linklocal($gatewayipv6) && !strpos($gatewayipv6, '%'))
554
				$ifscope = "%{$defaultifv6}";
555
			log_error("ROUTING: setting IPv6 default route to {$gatewayipv6}{$ifscope}");
556
			mwexec("/sbin/route change -inet6 default " . escapeshellarg("{$gatewayipv6}{$ifscope}"));
557
		}
558
	}
559

    
560
	system_staticroutes_configure($interface, false);
561

    
562
	return 0;
563
}
564

    
565
function system_staticroutes_configure($interface = "", $update_dns = false) {
566
	global $config, $g, $aliastable;
567

    
568
	$filterdns_list = array();
569

    
570
	$static_routes = get_staticroutes(false, true);
571
	if (count($static_routes)) {
572
		$gateways_arr = return_gateways_array(false, true);
573

    
574
		foreach ($static_routes as $rtent) {
575
			if (empty($gateways_arr[$rtent['gateway']])) {
576
				log_error(sprintf(gettext("Static Routes: Gateway IP could not be found for %s"), $rtent['network']));
577
				continue;
578
			}
579
			$gateway = $gateways_arr[$rtent['gateway']];
580
			if (!empty($interface) && $interface != $gateway['friendlyiface'])
581
				continue;
582

    
583
			$gatewayip = $gateway['gateway'];
584
			$interfacegw = $gateway['interface'];
585

    
586
			$blackhole = "";
587
			if (!strcasecmp("Null", substr($rtent['gateway'], 0, 3)))
588
				$blackhole = "-blackhole";
589

    
590
			if (!is_fqdn($rtent['network']) && !is_subnet($rtent['network']))
591
				continue;
592

    
593
			$dnscache = array();
594
			if ($update_dns === true) {
595
				if (is_subnet($rtent['network']))
596
					continue;
597
				$dnscache = explode("\n", trim(compare_hostname_to_dnscache($rtent['network'])));
598
				if (empty($dnscache))
599
					continue;
600
			}
601

    
602
			if (is_subnet($rtent['network']))
603
				$ips = array($rtent['network']);
604
			else {
605
				if (!isset($rtent['disabled']))
606
					$filterdns_list[] = $rtent['network'];
607
				$ips = add_hostname_to_watch($rtent['network']);
608
			}
609

    
610
			foreach ($dnscache as $ip) {
611
				if (in_array($ip, $ips))
612
					continue;
613
				mwexec("/sbin/route delete " . escapeshellarg($ip), true);
614
				if (isset($config['system']['route-debug'])) {
615
					$mt = microtime();
616
					log_error("ROUTING debug: $mt - route delete $ip ");
617
				}
618
			}
619

    
620
			if (isset($rtent['disabled'])) {
621
				/* XXX: This can break things by deleting routes that shouldn't be deleted - OpenVPN, dynamic routing scenarios, etc. redmine #3709 */
622
				foreach ($ips as $ip) {
623
					mwexec("/sbin/route delete " . escapeshellarg($ip), true);
624
					if (isset($config['system']['route-debug'])) {
625
						$mt = microtime();
626
						log_error("ROUTING debug: $mt - route delete $ip ");
627
					}
628
				}
629
				continue;
630
			}
631

    
632
			foreach ($ips as $ip) {
633
				if (is_ipaddrv4($ip))
634
					$ip .= "/32";
635
				// do NOT do the same check here on v6, is_ipaddrv6 returns true when including the CIDR mask. doing so breaks v6 routes
636
					
637
				$inet = (is_subnetv6($ip) ? "-inet6" : "-inet");
638

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

    
641
				if (is_subnet($ip))
642
					if (is_ipaddr($gatewayip)) {
643
						mwexec($cmd . escapeshellarg($gatewayip));
644
						if (isset($config['system']['route-debug'])) {
645
							$mt = microtime();
646
							log_error("ROUTING debug: $mt - $cmd $gatewayip");
647
						}
648
					} else if (!empty($interfacegw)) {
649
						mwexec($cmd . "-iface " . escapeshellarg($interfacegw));
650
						if (isset($config['system']['route-debug'])) {
651
							$mt = microtime();
652
							log_error("ROUTING debug: $mt - $cmd -iface $interfacegw ");
653
						}
654
					}
655
			}
656
		}
657
		unset($gateways_arr);
658
	}
659
	unset($static_routes);
660

    
661
	if ($update_dns === false) {
662
		if (count($filterdns_list)) {
663
			$interval = 60;
664
			$hostnames = "";
665
			array_unique($filterdns_list);
666
			foreach ($filterdns_list as $hostname)
667
				$hostnames .= "cmd {$hostname} '/usr/local/sbin/pfSctl -c \"service reload routedns\"'\n";
668
			file_put_contents("{$g['varetc_path']}/filterdns-route.hosts", $hostnames);
669
			unset($hostnames);
670

    
671
			if (isvalidpid("{$g['varrun_path']}/filterdns-route.pid"))
672
				sigkillbypid("{$g['varrun_path']}/filterdns-route.pid", "HUP");
673
			else
674
				mwexec("/usr/local/sbin/filterdns -p {$g['varrun_path']}/filterdns-route.pid -i {$interval} -c {$g['varetc_path']}/filterdns-route.hosts -d 1");
675
		} else {
676
			killbypid("{$g['varrun_path']}/filterdns-route.pid");
677
			@unlink("{$g['varrun_path']}/filterdns-route.pid");
678
		}
679
	}
680
	unset($filterdns_list);
681

    
682
	return 0;
683
}
684

    
685
function system_routing_enable() {
686
	global $config, $g;
687
	if(isset($config['system']['developerspew'])) {
688
		$mt = microtime();
689
		echo "system_routing_enable() being called $mt\n";
690
	}
691

    
692
	set_sysctl(array(
693
		"net.inet.ip.forwarding" => "1",
694
		"net.inet6.ip6.forwarding" => "1"
695
	));
696

    
697
	return;
698
}
699

    
700
function system_syslogd_fixup_server($server) {
701
	/* If it's an IPv6 IP alone, encase it in brackets */
702
	if (is_ipaddrv6($server))
703
		return "[$server]";
704
	else
705
		return $server;
706
}
707

    
708
function system_syslogd_get_remote_servers($syslogcfg, $facility = "*.*") {
709
	// Rather than repeatedly use the same code, use this function to build a list of remote servers.
710
	$facility .= " ".
711
	$remote_servers = "";
712
	$pad_to  = 56;
713
	$padding = ceil(($pad_to - strlen($facility))/8)+1;
714
	if($syslogcfg['remoteserver'])
715
		$remote_servers .= "{$facility}" . str_repeat("\t", $padding) . "@" . system_syslogd_fixup_server($syslogcfg['remoteserver']) . "\n";
716
	if($syslogcfg['remoteserver2'])
717
		$remote_servers .= "{$facility}" . str_repeat("\t", $padding) . "@" . system_syslogd_fixup_server($syslogcfg['remoteserver2']) . "\n";
718
	if($syslogcfg['remoteserver3'])
719
		$remote_servers .= "{$facility}" . str_repeat("\t", $padding) . "@" . system_syslogd_fixup_server($syslogcfg['remoteserver3']) . "\n";
720
	return $remote_servers;
721
}
722

    
723
function system_syslogd_start() {
724
	global $config, $g;
725
	if(isset($config['system']['developerspew'])) {
726
		$mt = microtime();
727
		echo "system_syslogd_start() being called $mt\n";
728
	}
729

    
730
	mwexec("/etc/rc.d/hostid start");
731

    
732
	$syslogcfg = $config['syslog'];
733

    
734
	if (platform_booting())
735
		echo gettext("Starting syslog...");
736

    
737
	if (is_process_running("fifolog_writer"))
738
		mwexec('/bin/pkill fifolog_writer');
739

    
740
	// Which logging type are we using this week??
741
	if (isset($config['system']['disablesyslogclog'])) {
742
		$log_directive = "";
743
		$log_create_directive = "/usr/bin/touch ";
744
		$log_size = "";
745
	} else if (isset($config['system']['usefifolog'])) {
746
		$log_directive = "|/usr/sbin/fifolog_writer ";
747
		$log_size = isset($config['syslog']['logfilesize']) ? $config['syslog']['logfilesize'] : "10240";
748
		$log_create_directive = "/usr/sbin/fifolog_create -s ";
749
	} else { // Defaults to CLOG
750
		$log_directive = "%";
751
		$log_size = isset($config['syslog']['logfilesize']) ? $config['syslog']['logfilesize'] : "10240";
752
		$log_create_directive = "/usr/local/sbin/clog -i -s ";
753
	}
754

    
755
	$syslogd_extra = "";
756
	if (isset($syslogcfg)) {
757
		$separatelogfacilities = array('ntp','ntpd','ntpdate','charon','ipsec_starter','openvpn','pptps','poes','l2tps','relayd','hostapd','dnsmasq','filterdns','unbound','dhcpd','dhcrelay','dhclient','dhcp6c','apinger','radvd','routed','olsrd','zebra','ospfd','bgpd','miniupnpd','filterlog');
758
		$syslogconf = "";
759
		if($config['installedpackages']['package']) {
760
			foreach($config['installedpackages']['package'] as $package) {
761
				if($package['logging']) {
762
					array_push($separatelogfacilities, $package['logging']['facilityname']);
763
					mwexec("{$log_create_directive} {$log_size} {$g['varlog_path']}/{$package['logging']['logfilename']}");
764
					$syslogconf .= "!{$package['logging']['facilityname']}\n*.*\t\t\t\t\t\t {$log_directive}{$g['varlog_path']}/{$package['logging']['logfilename']}\n";
765
				}
766
			}
767
		}
768
		$facilitylist = implode(',', array_unique($separatelogfacilities));
769
		$syslogconf .= "!radvd,routed,olsrd,zebra,ospfd,bgpd,miniupnpd\n";
770
		if (!isset($syslogcfg['disablelocallogging']))
771
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/routing.log\n";
772

    
773
		$syslogconf .= "!ntp,ntpd,ntpdate\n";
774
		if (!isset($syslogcfg['disablelocallogging'])) 
775
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/ntpd.log\n";
776

    
777
		$syslogconf .= "!ppp\n";
778
		if (!isset($syslogcfg['disablelocallogging'])) 
779
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/ppp.log\n";
780

    
781
		$syslogconf .= "!pptps\n";
782
		if (!isset($syslogcfg['disablelocallogging'])) 
783
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/pptps.log\n";
784

    
785
		$syslogconf .= "!poes\n";
786
		if (!isset($syslogcfg['disablelocallogging'])) 
787
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/poes.log\n";
788

    
789
		$syslogconf .= "!l2tps\n";
790
		if (!isset($syslogcfg['disablelocallogging'])) 
791
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/l2tps.log\n";
792

    
793
		$syslogconf .= "!charon,ipsec_starter\n";
794
		if (!isset($syslogcfg['disablelocallogging'])) 
795
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/ipsec.log\n";
796
		if (isset($syslogcfg['vpn']))
797
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "*.*");
798

    
799
		$syslogconf .= "!openvpn\n";
800
		if (!isset($syslogcfg['disablelocallogging'])) 
801
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/openvpn.log\n";
802
		if (isset($syslogcfg['vpn']))
803
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "*.*");
804

    
805
		$syslogconf .= "!apinger\n";
806
		if (!isset($syslogcfg['disablelocallogging']))
807
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/gateways.log\n";
808
		if (isset($syslogcfg['apinger']))
809
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "*.*");
810

    
811
		$syslogconf .= "!dnsmasq,filterdns,unbound\n";
812
		if (!isset($syslogcfg['disablelocallogging']))
813
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/resolver.log\n";
814

    
815
		$syslogconf .= "!dhcpd,dhcrelay,dhclient,dhcp6c\n";
816
		if (!isset($syslogcfg['disablelocallogging']))
817
			$syslogconf .= "*.*								{$log_directive}{$g['varlog_path']}/dhcpd.log\n";
818
		if (isset($syslogcfg['dhcp']))
819
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "*.*");
820

    
821
		$syslogconf .= "!relayd\n";
822
		if (!isset($syslogcfg['disablelocallogging']))
823
			$syslogconf .= "*.* 								{$log_directive}{$g['varlog_path']}/relayd.log\n";
824
		if (isset($syslogcfg['relayd']))
825
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "*.*");
826

    
827
		$syslogconf .= "!hostapd\n";
828
		if (!isset($syslogcfg['disablelocallogging']))
829
			$syslogconf .= "*.* 								{$log_directive}{$g['varlog_path']}/wireless.log\n";
830
		if (isset($syslogcfg['hostapd']))
831
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "*.*");
832

    
833
		$syslogconf .= "!filterlog\n";
834
		$syslogconf .= "*.* 								{$log_directive}{$g['varlog_path']}/filter.log\n";
835
		if (isset($syslogcfg['filter']))
836
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "*.*");
837

    
838
		$syslogconf .= "!-{$facilitylist}\n";
839
		if (!isset($syslogcfg['disablelocallogging'])) 
840
			$syslogconf .= <<<EOD
841
local3.*							{$log_directive}{$g['varlog_path']}/vpn.log
842
local4.*							{$log_directive}{$g['varlog_path']}/portalauth.log
843
local7.*							{$log_directive}{$g['varlog_path']}/dhcpd.log
844
*.notice;kern.debug;lpr.info;mail.crit;daemon.none;		{$log_directive}{$g['varlog_path']}/system.log
845
news.err;local0.none;local3.none;local4.none;			{$log_directive}{$g['varlog_path']}/system.log
846
local7.none							{$log_directive}{$g['varlog_path']}/system.log
847
security.*							{$log_directive}{$g['varlog_path']}/system.log
848
auth.info;authpriv.info;daemon.info				{$log_directive}{$g['varlog_path']}/system.log
849
auth.info;authpriv.info 					|exec /usr/local/sbin/sshlockout_pf 15
850
*.emerg								*
851

    
852
EOD;
853
		if (isset($syslogcfg['vpn']))
854
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "local3.*");
855
		if (isset($syslogcfg['portalauth']))
856
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "local4.*");
857
		if (isset($syslogcfg['dhcp']))
858
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "local7.*");
859
		if (isset($syslogcfg['system'])) {
860
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "*.notice;kern.debug;lpr.info;mail.crit;");
861
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "news.err;local0.none;local3.none;local7.none");
862
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "security.*");
863
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "auth.info;authpriv.info;daemon.info");
864
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "*.emerg");
865
		}
866
		if (isset($syslogcfg['logall'])) {
867
			// Make everything mean everything, including facilities excluded above.
868
			$syslogconf .= "!*\n";
869
			$syslogconf .= system_syslogd_get_remote_servers($syslogcfg, "*.*");
870
		}
871

    
872
		if (isset($syslogcfg['zmqserver'])) {
873
				$syslogconf .= <<<EOD
874
*.*								^{$syslogcfg['zmqserver']}
875

    
876
EOD;
877
		}
878
		/* write syslog.conf */		
879
		if (!@file_put_contents("{$g['varetc_path']}/syslog.conf", $syslogconf)) {
880
			printf(gettext("Error: cannot open syslog.conf in system_syslogd_start().%s"), "\n");
881
			unset($syslogconf);
882
			return 1;
883
		}
884
		unset($syslogconf);
885

    
886
		// Ensure that the log directory exists
887
		if (!is_dir("{$g['dhcpd_chroot_path']}/var/run"))
888
			exec("/bin/mkdir -p {$g['dhcpd_chroot_path']}/var/run");
889

    
890
		$sourceip = "";
891
		if (!empty($syslogcfg['sourceip'])) {
892
			if ($syslogcfg['ipproto'] == "ipv6") {
893
				$ifaddr = is_ipaddr($syslogcfg['sourceip']) ? $syslogcfg['sourceip'] : get_interface_ipv6($syslogcfg['sourceip']);
894
				if (!is_ipaddr($ifaddr))
895
					$ifaddr = get_interface_ip($syslogcfg['sourceip']);
896
			} else {
897
				$ifaddr = is_ipaddr($syslogcfg['sourceip']) ? $syslogcfg['sourceip'] : get_interface_ip($syslogcfg['sourceip']);
898
				if (!is_ipaddr($ifaddr))
899
					$ifaddr = get_interface_ipv6($syslogcfg['sourceip']);
900
			}
901
			if (is_ipaddr($ifaddr)) {
902
				$sourceip = "-b {$ifaddr}";
903
			}
904
		}
905

    
906
		$syslogd_extra = "-f {$g['varetc_path']}/syslog.conf {$sourceip}";
907
	}
908

    
909
	if (isvalidpid("{$g['varrun_path']}/syslog.pid")) {
910
		sigkillbypid("{$g['varrun_path']}/syslog.pid", "TERM");
911
		usleep(100000); // syslogd often doesn't respond to a TERM quickly enough for the starting of syslogd below to be successful
912
	}
913
	
914
	if (isvalidpid("{$g['varrun_path']}/syslog.pid")) {
915
		// if it still hasn't responded to the TERM, KILL it. 
916
		sigkillbypid("{$g['varrun_path']}/syslog.pid", "KILL");
917
		usleep(100000); 
918
	}
919

    
920
	
921
	$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}");
922

    
923
	if (platform_booting())
924
		echo gettext("done.") . "\n";
925

    
926
	return $retval;
927
}
928

    
929
function system_webgui_create_certificate() {
930
	global $config, $g;
931

    
932
	if (!is_array($config['ca']))
933
		$config['ca'] = array();
934
	$a_ca =& $config['ca'];
935
	if (!is_array($config['cert']))
936
		$config['cert'] = array();
937
	$a_cert =& $config['cert'];
938
	log_error("Creating SSL Certificate for this host");
939

    
940
	$cert = array();
941
	$cert['refid'] = uniqid();
942
	$cert['descr'] = gettext("webConfigurator default ({$cert['refid']})");
943

    
944
	$dn = array(
945
		'countryName' => "US",
946
		'stateOrProvinceName' => "State",
947
		'localityName' => "Locality",
948
		'organizationName' => "{$g['product_name']} webConfigurator Self-Signed Certificate",
949
		'emailAddress' => "admin@{$config['system']['hostname']}.{$config['system']['domain']}",
950
		'commonName' => "{$config['system']['hostname']}-{$cert['refid']}");
951
	$old_err_level = error_reporting(0); /* otherwise openssl_ functions throw warnings directly to a page screwing menu tab */
952
	if (!cert_create($cert, null, 2048, 2000, $dn, "self-signed", "sha256")){
953
		while($ssl_err = openssl_error_string()){
954
			log_error("Error creating WebGUI Certificate: openssl library returns: " . $ssl_err);
955
		}
956
		error_reporting($old_err_level);
957
		return null;
958
	}
959
	error_reporting($old_err_level);
960

    
961
	$a_cert[] = $cert;
962
	$config['system']['webgui']['ssl-certref'] = $cert['refid'];
963
	write_config(gettext("Generated new self-signed HTTPS certificate ({$cert['refid']})"));
964
	return $cert;
965
}
966

    
967
function system_webgui_start() {
968
	global $config, $g;
969

    
970
	if (platform_booting())
971
		echo gettext("Starting webConfigurator...");
972

    
973
	chdir($g['www_path']);
974

    
975
	/* defaults */
976
	$portarg = "80";
977
	$crt = "";
978
	$key = "";
979
	$ca = "";
980

    
981
	/* non-standard port? */
982
	if (isset($config['system']['webgui']['port']) && $config['system']['webgui']['port'] <> "")
983
		$portarg = "{$config['system']['webgui']['port']}";
984

    
985
	if ($config['system']['webgui']['protocol'] == "https") {
986
		// Ensure that we have a webConfigurator CERT
987
		$cert =& lookup_cert($config['system']['webgui']['ssl-certref']);
988
		if(!is_array($cert) || !$cert['crt'] || !$cert['prv'])
989
			$cert = system_webgui_create_certificate();
990
		$crt = base64_decode($cert['crt']);
991
		$key = base64_decode($cert['prv']);
992

    
993
		if(!$config['system']['webgui']['port'])
994
			$portarg = "443";
995
		$ca  = ca_chain($cert);
996
	}
997

    
998
	/* generate lighttpd configuration */
999
	system_generate_lighty_config("{$g['varetc_path']}/lighty-webConfigurator.conf",
1000
		$crt, $key, $ca, "lighty-webConfigurator.pid", $portarg, "/usr/local/www/",
1001
		"cert.pem", "ca.pem");
1002

    
1003
	/* kill any running lighttpd */
1004
	killbypid("{$g['varrun_path']}/lighty-webConfigurator.pid");
1005

    
1006
	sleep(1);
1007

    
1008
	@unlink("{$g['varrun_path']}/lighty-webConfigurator.pid");
1009

    
1010
	/* attempt to start lighthttpd */
1011
	$res = mwexec("/usr/local/sbin/lighttpd -f {$g['varetc_path']}/lighty-webConfigurator.conf");
1012

    
1013
	if (platform_booting()) {
1014
		if ($res == 0)
1015
			echo gettext("done.") . "\n";
1016
		else
1017
			echo gettext("failed!") . "\n";
1018
	}
1019

    
1020
	return $res;
1021
}
1022

    
1023
function system_generate_lighty_config($filename,
1024
	$cert,
1025
	$key,
1026
	$ca,
1027
	$pid_file,
1028
	$port = 80,
1029
	$document_root = "/usr/local/www/",
1030
	$cert_location = "cert.pem",
1031
	$ca_location = "ca.pem",
1032
	$captive_portal = false) {
1033

    
1034
	global $config, $g;
1035

    
1036
	if(!is_dir("{$g['tmp_path']}/lighttpdcompress"))
1037
		mkdir("{$g['tmp_path']}/lighttpdcompress");
1038

    
1039
	if(isset($config['system']['developerspew'])) {
1040
		$mt = microtime();
1041
		echo "system_generate_lighty_config() being called $mt\n";
1042
	}
1043

    
1044
	if ($captive_portal !== false)  {
1045
		$captiveportal = ",\"mod_rewrite\",\"mod_evasive\"";
1046
		$captive_portal_rewrite = "url.rewrite-once = ( \"(.*captiveportal.*)\" => \"$1\", \"(.*)\" => \"/index.php?zone={$captive_portal}&redirurl=$1\" )\n";
1047

    
1048
		$maxprocperip = $config['captiveportal'][$captive_portal]['maxprocperip'];
1049
		if (empty($maxprocperip))
1050
			$maxprocperip = 10;
1051
		$captive_portal_mod_evasive = "evasive.max-conns-per-ip = {$maxprocperip}";
1052

    
1053
		$server_upload_dirs = "server.upload-dirs = ( \"{$g['tmp_path']}/captiveportal/\" )\n";
1054
		if(!is_dir("{$g['tmp_path']}/captiveportal"))
1055
			@mkdir("{$g['tmp_path']}/captiveportal", 0555);
1056
		$server_max_request_size = "server.max-request-size    = 384";
1057
		$cgi_config = "";
1058
	} else {
1059
		$captiveportal = ",\"mod_cgi\"";
1060
		$captive_portal_rewrite = "";
1061
		$captive_portal_mod_evasive = "";
1062
		$server_upload_dirs = "server.upload-dirs = ( \"{$g['upload_path']}/\", \"{$g['tmp_path']}/\", \"/var/\" )\n";
1063
		$server_max_request_size = "server.max-request-size    = 2097152";
1064
		$cgi_config = "cgi.assign                 = ( \".cgi\" => \"\" )";
1065
	}
1066
	
1067
	if (empty($port))
1068
		$lighty_port = "80";
1069
	else
1070
		$lighty_port = $port;
1071

    
1072
	$memory = get_memory();
1073
	$realmem = $memory[1];
1074

    
1075
	// Determine web GUI process settings and take into account low memory systems
1076
	if ($realmem < 255)
1077
		$max_procs = 1;
1078
	else
1079
		$max_procs = ($config['system']['webgui']['max_procs']) ? $config['system']['webgui']['max_procs'] : 2;
1080

    
1081
	// Ramp up captive portal max procs, assuming each PHP process can consume up to 64MB RAM 
1082
	if ($captive_portal !== false)  {
1083
		if ($realmem > 135 and $realmem < 256) {
1084
			$max_procs += 1; // 2 worker processes
1085
		} else if ($realmem > 255 and $realmem < 513) {
1086
			$max_procs += 2; // 3 worker processes
1087
		} else if ($realmem > 512) {
1088
			$max_procs += 4; // 6 worker processes
1089
		}
1090
		if ($max_procs > 1)
1091
			$max_php_children = intval($max_procs/2);
1092
		else
1093
			$max_php_children = 1;
1094

    
1095
	} else {
1096
		if ($realmem < 78)
1097
			$max_php_children = 0;
1098
		else
1099
			$max_php_children = 1;
1100
	}
1101

    
1102
	if(!isset($config['syslog']['nologlighttpd'])) {
1103
		$lighty_use_syslog = <<<EOD
1104
## where to send error-messages to
1105
server.errorlog-use-syslog="enable"
1106
EOD;
1107
	}
1108

    
1109

    
1110
	if ($captive_portal !== false) {
1111
		$fast_cgi_path = "{$g['tmp_path']}/php-fastcgi-{$captive_portal}.socket";
1112
		$fastcgi_config = <<<EOD
1113
#### fastcgi module
1114
## read fastcgi.txt for more info
1115
fastcgi.server = ( ".php" =>
1116
	( "localhost" =>
1117
		(
1118
			"socket" => "{$fast_cgi_path}",
1119
			"max-procs" => {$max_procs},
1120
			"bin-environment" => (
1121
				"PHP_FCGI_CHILDREN" => "{$max_php_children}",
1122
				"PHP_FCGI_MAX_REQUESTS" => "500"
1123
			),
1124
			"bin-path" => "/usr/local/bin/php"
1125
		)
1126
	)
1127
)
1128

    
1129
EOD;
1130
	} else {
1131
		$fast_cgi_path = "{$g['varrun_path']}/php-fpm.socket";
1132
		$fastcgi_config = <<<EOD
1133
#### fastcgi module
1134
## read fastcgi.txt for more info
1135
fastcgi.server = ( ".php" =>
1136
	( "localhost" =>
1137
		(
1138
			"socket" => "{$fast_cgi_path}",
1139
			"broken-scriptfilename" => "enable"
1140
		)
1141
	)
1142
)
1143

    
1144
EOD;
1145
	}
1146

    
1147

    
1148
	$lighty_config = <<<EOD
1149
#
1150
# lighttpd configuration file
1151
#
1152
# use a it as base for lighttpd 1.0.0 and above
1153
#
1154
############ Options you really have to take care of ####################
1155

    
1156
## FreeBSD!
1157
server.event-handler	= "freebsd-kqueue"
1158
server.network-backend 	= "writev"
1159
#server.use-ipv6 = "enable"
1160

    
1161
## modules to load
1162
server.modules              =   ( "mod_access", "mod_expire", "mod_compress", "mod_redirect",
1163
	{$captiveportal}, "mod_fastcgi"
1164
)
1165

    
1166
server.max-keep-alive-requests = 15
1167
server.max-keep-alive-idle = 30
1168

    
1169
## a static document-root, for virtual-hosting take look at the
1170
## server.virtual-* options
1171
server.document-root        = "{$document_root}"
1172
{$captive_portal_rewrite}
1173

    
1174
# Maximum idle time with nothing being written (php downloading)
1175
server.max-write-idle = 999
1176

    
1177
{$lighty_use_syslog}
1178

    
1179
# files to check for if .../ is requested
1180
server.indexfiles           = ( "index.php", "index.html",
1181
                                "index.htm", "default.htm" )
1182

    
1183
# mimetype mapping
1184
mimetype.assign             = (
1185
  ".pdf"          =>      "application/pdf",
1186
  ".sig"          =>      "application/pgp-signature",
1187
  ".spl"          =>      "application/futuresplash",
1188
  ".class"        =>      "application/octet-stream",
1189
  ".ps"           =>      "application/postscript",
1190
  ".torrent"      =>      "application/x-bittorrent",
1191
  ".dvi"          =>      "application/x-dvi",
1192
  ".gz"           =>      "application/x-gzip",
1193
  ".pac"          =>      "application/x-ns-proxy-autoconfig",
1194
  ".swf"          =>      "application/x-shockwave-flash",
1195
  ".tar.gz"       =>      "application/x-tgz",
1196
  ".tgz"          =>      "application/x-tgz",
1197
  ".tar"          =>      "application/x-tar",
1198
  ".zip"          =>      "application/zip",
1199
  ".mp3"          =>      "audio/mpeg",
1200
  ".m3u"          =>      "audio/x-mpegurl",
1201
  ".wma"          =>      "audio/x-ms-wma",
1202
  ".wax"          =>      "audio/x-ms-wax",
1203
  ".ogg"          =>      "audio/x-wav",
1204
  ".wav"          =>      "audio/x-wav",
1205
  ".gif"          =>      "image/gif",
1206
  ".jpg"          =>      "image/jpeg",
1207
  ".jpeg"         =>      "image/jpeg",
1208
  ".png"          =>      "image/png",
1209
  ".xbm"          =>      "image/x-xbitmap",
1210
  ".xpm"          =>      "image/x-xpixmap",
1211
  ".xwd"          =>      "image/x-xwindowdump",
1212
  ".css"          =>      "text/css",
1213
  ".html"         =>      "text/html",
1214
  ".htm"          =>      "text/html",
1215
  ".js"           =>      "text/javascript",
1216
  ".asc"          =>      "text/plain",
1217
  ".c"            =>      "text/plain",
1218
  ".conf"         =>      "text/plain",
1219
  ".text"         =>      "text/plain",
1220
  ".txt"          =>      "text/plain",
1221
  ".dtd"          =>      "text/xml",
1222
  ".xml"          =>      "text/xml",
1223
  ".mpeg"         =>      "video/mpeg",
1224
  ".mpg"          =>      "video/mpeg",
1225
  ".mov"          =>      "video/quicktime",
1226
  ".qt"           =>      "video/quicktime",
1227
  ".avi"          =>      "video/x-msvideo",
1228
  ".asf"          =>      "video/x-ms-asf",
1229
  ".asx"          =>      "video/x-ms-asf",
1230
  ".wmv"          =>      "video/x-ms-wmv",
1231
  ".bz2"          =>      "application/x-bzip",
1232
  ".tbz"          =>      "application/x-bzip-compressed-tar",
1233
  ".tar.bz2"      =>      "application/x-bzip-compressed-tar"
1234
 )
1235

    
1236
# Use the "Content-Type" extended attribute to obtain mime type if possible
1237
#mimetypes.use-xattr        = "enable"
1238

    
1239
## deny access the file-extensions
1240
#
1241
# ~    is for backupfiles from vi, emacs, joe, ...
1242
# .inc is often used for code includes which should in general not be part
1243
#      of the document-root
1244
url.access-deny             = ( "~", ".inc" )
1245

    
1246

    
1247
######### Options that are good to be but not necessary to be changed #######
1248

    
1249
## bind to port (default: 80)
1250

    
1251
EOD;
1252

    
1253
	$lighty_config .= "server.bind  = \"0.0.0.0\"\n";
1254
	$lighty_config .= "server.port  = {$lighty_port}\n";
1255
	$lighty_config .= "\$SERVER[\"socket\"]  == \"0.0.0.0:{$lighty_port}\" { }\n";
1256
	$lighty_config .= "\$SERVER[\"socket\"]  == \"[::]:{$lighty_port}\" { \n";
1257
	if($cert <> "" and $key <> "") {
1258
		$lighty_config .= "\n";
1259
		$lighty_config .= "## ssl configuration\n";
1260
		$lighty_config .= "ssl.engine = \"enable\"\n";
1261
		$lighty_config .= "ssl.pemfile = \"{$g['varetc_path']}/{$cert_location}\"\n\n";
1262
		if($ca <> "")
1263
			$lighty_config .= "ssl.ca-file = \"{$g['varetc_path']}/{$ca_location}\"\n\n";
1264
	}
1265
	$lighty_config .= " }\n";
1266

    
1267

    
1268
	$lighty_config .= <<<EOD
1269

    
1270
## error-handler for status 404
1271
#server.error-handler-404   = "/error-handler.html"
1272
#server.error-handler-404   = "/error-handler.php"
1273

    
1274
## to help the rc.scripts
1275
server.pid-file            = "{$g['varrun_path']}/{$pid_file}"
1276

    
1277
## virtual directory listings
1278
server.dir-listing         = "disable"
1279

    
1280
## enable debugging
1281
debug.log-request-header   = "disable"
1282
debug.log-response-header  = "disable"
1283
debug.log-request-handling = "disable"
1284
debug.log-file-not-found   = "disable"
1285

    
1286
# gzip compression
1287
compress.cache-dir = "{$g['tmp_path']}/lighttpdcompress/"
1288
compress.filetype  = ("text/plain","text/css", "text/xml", "text/javascript" )
1289

    
1290
{$server_upload_dirs}
1291

    
1292
{$server_max_request_size}
1293

    
1294
{$fastcgi_config}
1295

    
1296
{$cgi_config}
1297

    
1298
{$captive_portal_mod_evasive}
1299

    
1300
expire.url = (
1301
				"" => "access 50 hours",	
1302
        )
1303

    
1304
EOD;
1305

    
1306
	$cert = str_replace("\r", "", $cert);
1307
	$key = str_replace("\r", "", $key);
1308
	$ca = str_replace("\r", "", $ca);
1309

    
1310
	$cert = str_replace("\n\n", "\n", $cert);
1311
	$key = str_replace("\n\n", "\n", $key);
1312
	$ca = str_replace("\n\n", "\n", $ca);
1313

    
1314
	if($cert <> "" and $key <> "") {
1315
		$fd = fopen("{$g['varetc_path']}/{$cert_location}", "w");
1316
		if (!$fd) {
1317
			printf(gettext("Error: cannot open cert.pem in system_webgui_start().%s"), "\n");
1318
			return 1;
1319
		}
1320
		chmod("{$g['varetc_path']}/{$cert_location}", 0600);
1321
		fwrite($fd, $cert);
1322
		fwrite($fd, "\n");
1323
		fwrite($fd, $key);
1324
		fclose($fd);
1325
		if(!(empty($ca) || (strlen(trim($ca)) == 0))) {
1326
			$fd = fopen("{$g['varetc_path']}/{$ca_location}", "w");
1327
			if (!$fd) {
1328
				printf(gettext("Error: cannot open ca.pem in system_webgui_start().%s"), "\n");
1329
				return 1;
1330
			}
1331
			chmod("{$g['varetc_path']}/{$ca_location}", 0600);
1332
			fwrite($fd, $ca);
1333
			fclose($fd);
1334
		}
1335
		$lighty_config .= "\n";
1336
		$lighty_config .= "## " . gettext("ssl configuration") . "\n";
1337
		$lighty_config .= "ssl.engine = \"enable\"\n";
1338
		$lighty_config .= "ssl.pemfile = \"{$g['varetc_path']}/{$cert_location}\"\n\n";
1339

    
1340
		// SSLv2/3 is deprecated, force use of TLS
1341
		$lighty_config .= "ssl.use-sslv2 = \"disable\"\n";
1342
		$lighty_config .= "ssl.use-sslv3 = \"disable\"\n";
1343

    
1344
		// where ssl.cipher-list is set, this is automatically enabled, but set it explicitly anyway.
1345
		$lighty_config .= "ssl.honor-cipher-order = \"enable\"\n";
1346

    
1347
		$lighty_config .= "ssl.cipher-list = \"AES128+EECDH:AES256+EECDH:AES128+EDH:AES256+EDH:AES128-SHA:AES256-SHA:!aNULL:!eNULL:!DSS\"\n";
1348

    
1349
		if(!(empty($ca) || (strlen(trim($ca)) == 0)))
1350
			$lighty_config .= "ssl.ca-file = \"{$g['varetc_path']}/{$ca_location}\"\n\n";
1351
	}
1352

    
1353
	// Add HTTP to HTTPS redirect	
1354
	if ($captive_portal === false && $config['system']['webgui']['protocol'] == "https" && !isset($config['system']['webgui']['disablehttpredirect'])) {
1355
		if($lighty_port != "443") 
1356
			$redirectport = ":{$lighty_port}";
1357
		$lighty_config .= <<<EOD
1358
\$SERVER["socket"] == ":80" {
1359
	\$HTTP["host"] =~ "(.*)" {
1360
		url.redirect = ( "^/(.*)" => "https://%1{$redirectport}/$1" )
1361
	}
1362
}
1363
\$SERVER["socket"] == "[::]:80" {
1364
	\$HTTP["host"] =~ "(.*)" {
1365
		url.redirect = ( "^/(.*)" => "https://%1{$redirectport}/$1" )
1366
	}
1367
}
1368
EOD;
1369
	}
1370

    
1371
	$fd = fopen("{$filename}", "w");
1372
	if (!$fd) {
1373
		printf(gettext("Error: cannot open %s in system_generate_lighty_config().%s"), $filename, "\n");
1374
		return 1;
1375
	}
1376
	fwrite($fd, $lighty_config);
1377
	fclose($fd);
1378

    
1379
	return 0;
1380

    
1381
}
1382

    
1383
function system_timezone_configure() {
1384
	global $config, $g;
1385
	if(isset($config['system']['developerspew'])) {
1386
		$mt = microtime();
1387
		echo "system_timezone_configure() being called $mt\n";
1388
	}
1389

    
1390
	$syscfg = $config['system'];
1391

    
1392
	if (platform_booting())
1393
		echo gettext("Setting timezone...");
1394

    
1395
	/* extract appropriate timezone file */
1396
	$timezone = $syscfg['timezone'];
1397
	if ($timezone) {
1398
		exec('/usr/bin/tar -tvzf /usr/share/zoneinfo.tgz', $tzs);
1399
		foreach ($tzs as $tz) {
1400
			if (preg_match(",{$timezone}$,", $tz))
1401
				break;
1402
			if (preg_match(",{$timezone} link to *(.*)$,", $tz, $matches)) {
1403
				$timezone = $matches[1];
1404
				break;
1405
			}
1406
		}
1407
	} else
1408
		$timezone = "Etc/UTC";
1409

    
1410
	conf_mount_rw();
1411

    
1412
	exec("LANG=C /usr/bin/tar xzfO /usr/share/zoneinfo.tgz " .
1413
		escapeshellarg($timezone) . " > /etc/localtime");
1414

    
1415
	mwexec("sync");
1416
	conf_mount_ro();
1417

    
1418
	if (platform_booting())
1419
		echo gettext("done.") . "\n";
1420
}
1421

    
1422
function system_ntp_setup_gps($serialport) {
1423
	global $config, $g;
1424
	$gps_device = '/dev/gps0';
1425
	$serialport = '/dev/'.$serialport;
1426

    
1427
	if (!file_exists($serialport))
1428
		return false;
1429

    
1430
	conf_mount_rw();
1431
	// Create symlink that ntpd requires
1432
	unlink_if_exists($gps_device);
1433
	@symlink($serialport, $gps_device);
1434

    
1435
	/* Send the following to the GPS port to initialize the GPS */
1436
	if (is_array($config['ntpd']) && is_array($config['ntpd']['gps']) && !empty($config['ntpd']['gps']['type'])) {
1437
		$gps_init = base64_decode($config['ntpd']['gps']['initcmd']);
1438
	}else{
1439
		$gps_init = base64_decode('JFBVQlgsNDAsR1NWLDAsMCwwLDAqNTkNCiRQVUJYLDQwLEdMTCwwLDAsMCwwKjVDDQokUFVCWCw0MCxaREEsMCwwLDAsMCo0NA0KJFBVQlgsNDAsVlRHLDAsMCwwLDAqNUUNCiRQVUJYLDQwLEdTViwwLDAsMCwwKjU5DQokUFVCWCw0MCxHU0EsMCwwLDAsMCo0RQ0KJFBVQlgsNDAsR0dBLDAsMCwwLDANCiRQVUJYLDQwLFRYVCwwLDAsMCwwDQokUFVCWCw0MCxSTUMsMCwwLDAsMCo0Ng0KJFBVQlgsNDEsMSwwMDA3LDAwMDMsNDgwMCwwDQokUFVCWCw0MCxaREEsMSwxLDEsMQ==');
1440
	}
1441

    
1442
	/* XXX: Why not file_put_contents to the device */
1443
	@file_put_contents('/tmp/gps.init', $gps_init);
1444
	`cat /tmp/gps.init > $serialport`;
1445

    
1446
	/* Add /etc/remote entry in case we need to read from the GPS with tip */
1447
	if (intval(`grep -c '^gps0' /etc/remote`) == 0) {
1448
		$gpsbaud = '4800';
1449
		if (is_array($config['ntpd']) && is_array($config['ntpd']['gps']) && !empty($config['ntpd']['gps']['speed'])) {
1450
			switch($config['ntpd']['gps']['speed']) {
1451
				case '16':
1452
					$gpsbaud = '9600';
1453
					break;
1454
				case '32':
1455
					$gpsbaud = '19200';
1456
					break;
1457
				case '48':
1458
					$gpsbaud = '38400';
1459
					break;
1460
				case '64':
1461
					$gpsbaud = '57600';
1462
					break;
1463
				case '80':
1464
					$gpsbaud = '115200';
1465
					break;
1466
			}
1467
		}
1468
		@file_put_contents("/etc/remote", "gps0:dv={$serialport}:br#{$gpsbaud}:pa=none:", FILE_APPEND);
1469
	}
1470

    
1471
	conf_mount_ro();
1472

    
1473
	return true;
1474
}
1475

    
1476
function system_ntp_setup_pps($serialport) {
1477
	global $config, $g;
1478

    
1479
	$pps_device = '/dev/pps0';
1480
	$serialport = '/dev/'.$serialport;
1481

    
1482
	if (!file_exists($serialport))
1483
		return false;
1484

    
1485
	conf_mount_rw();
1486
	// Create symlink that ntpd requires
1487
	unlink_if_exists($pps_device);
1488
	@symlink($serialport, $pps_device);
1489

    
1490
	conf_mount_ro();
1491

    
1492
	return true;
1493
}
1494

    
1495

    
1496
function system_ntp_configure($start_ntpd=true) {
1497
	global $config, $g;
1498

    
1499
	$driftfile = "/var/db/ntpd.drift";
1500
	$statsdir = "/var/log/ntp";
1501
	$gps_device = '/dev/gps0';
1502

    
1503
	if ($g['platform'] == 'jail')
1504
		return;
1505

    
1506
	safe_mkdir($statsdir);
1507

    
1508
	if (!is_array($config['ntpd']))
1509
		$config['ntpd'] = array();
1510

    
1511
	$ntpcfg = "# \n";
1512
	$ntpcfg .= "# pfSense ntp configuration file \n";
1513
	$ntpcfg .= "# \n\n";
1514
	$ntpcfg .= "tinker panic 0 \n";
1515

    
1516
	/* Add Orphan mode */
1517
	$ntpcfg .= "# Orphan mode stratum\n";
1518
	$ntpcfg .= 'tos orphan ';
1519
	if (!empty($config['ntpd']['orphan'])) {
1520
		$ntpcfg .= $config['ntpd']['orphan'];
1521
	}else{
1522
		$ntpcfg .= '12';
1523
	}
1524
	$ntpcfg .= "\n";
1525

    
1526
	/* Add PPS configuration */
1527
	if (is_array($config['ntpd']['pps']) && !empty($config['ntpd']['pps']['port'])
1528
		&& file_exists('/dev/'.$config['ntpd']['pps']['port'])
1529
		&& system_ntp_setup_pps($config['ntpd']['pps']['port'])) {
1530
		$ntpcfg .= "\n";
1531
		$ntpcfg .= "# PPS Setup\n";
1532
		$ntpcfg .= 'server 127.127.22.0';
1533
		$ntpcfg .= ' minpoll 4 maxpoll 4';
1534
		if (empty($config['ntpd']['pps']['prefer'])) { /*note: this one works backwards */
1535
			$ntpcfg .= ' prefer'; 
1536
		}
1537
		if (!empty($config['ntpd']['pps']['noselect'])) {
1538
			$ntpcfg .= ' noselect ';
1539
		}
1540
		$ntpcfg .= "\n";
1541
		$ntpcfg .= 'fudge 127.127.22.0';
1542
		if (!empty($config['ntpd']['pps']['fudge1'])) {
1543
			$ntpcfg .= ' time1 ';
1544
			$ntpcfg .= $config['ntpd']['pps']['fudge1'];
1545
		}
1546
		if (!empty($config['ntpd']['pps']['flag2'])) {
1547
			$ntpcfg .= ' flag2 1';
1548
		}
1549
		if (!empty($config['ntpd']['pps']['flag3'])) {
1550
			$ntpcfg .= ' flag3 1';
1551
		}else{
1552
			$ntpcfg .= ' flag3 0';
1553
		}
1554
		if (!empty($config['ntpd']['pps']['flag4'])) {
1555
			$ntpcfg .= ' flag4 1';
1556
		}
1557
		if (!empty($config['ntpd']['pps']['refid'])) {
1558
			$ntpcfg .= ' refid ';
1559
			$ntpcfg .= $config['ntpd']['pps']['refid'];
1560
		}
1561
		$ntpcfg .= "\n";
1562
	}
1563
	/* End PPS configuration */
1564

    
1565
	/* Add GPS configuration */
1566
	if (is_array($config['ntpd']['gps']) && !empty($config['ntpd']['gps']['port'])
1567
		&& file_exists('/dev/'.$config['ntpd']['gps']['port'])
1568
		&& system_ntp_setup_gps($config['ntpd']['gps']['port'])) {
1569
		$ntpcfg .= "\n";
1570
		$ntpcfg .= "# GPS Setup\n";
1571
		$ntpcfg .= 'server 127.127.20.0 mode ';
1572
		if (!empty($config['ntpd']['gps']['nmea']) || !empty($config['ntpd']['gps']['speed']) || !empty($config['ntpd']['gps']['subsec'])) {
1573
			if (!empty($config['ntpd']['gps']['nmea'])) {
1574
				$ntpmode = (int) $config['ntpd']['gps']['nmea'];
1575
			}
1576
			if (!empty($config['ntpd']['gps']['speed'])) {
1577
				$ntpmode += (int) $config['ntpd']['gps']['speed'];
1578
			}
1579
			if (!empty($config['ntpd']['gps']['subsec'])) {
1580
				$ntpmode += 128;
1581
			}
1582
			$ntpcfg .= (string) $ntpmode;
1583
		}else{
1584
			$ntpcfg .= '0';
1585
		}
1586
		$ntpcfg .= ' minpoll 4 maxpoll 4';
1587
		if (empty($config['ntpd']['gps']['prefer'])) { /*note: this one works backwards */
1588
			$ntpcfg .= ' prefer'; 
1589
		}
1590
		if (!empty($config['ntpd']['gps']['noselect'])) {
1591
			$ntpcfg .= ' noselect ';
1592
		}
1593
		$ntpcfg .= "\n";
1594
		$ntpcfg .= 'fudge 127.127.20.0';
1595
		if (!empty($config['ntpd']['gps']['fudge1'])) {
1596
			$ntpcfg .= ' time1 ';
1597
			$ntpcfg .= $config['ntpd']['gps']['fudge1'];
1598
		}
1599
		if (!empty($config['ntpd']['gps']['fudge2'])) {
1600
			$ntpcfg .= ' time2 ';
1601
			$ntpcfg .= $config['ntpd']['gps']['fudge2'];
1602
		}
1603
		if (!empty($config['ntpd']['gps']['flag1'])) {
1604
			$ntpcfg .= ' flag1 1';
1605
		}else{
1606
			$ntpcfg .= ' flag1 0';
1607
		}
1608
		if (!empty($config['ntpd']['gps']['flag2'])) {
1609
			$ntpcfg .= ' flag2 1';
1610
		}
1611
		if (!empty($config['ntpd']['gps']['flag3'])) {
1612
			$ntpcfg .= ' flag3 1';
1613
		}else{
1614
			$ntpcfg .= ' flag3 0';
1615
		}
1616
		if (!empty($config['ntpd']['gps']['flag4'])) {
1617
			$ntpcfg .= ' flag4 1';
1618
		}
1619
		if (!empty($config['ntpd']['gps']['refid'])) {
1620
			$ntpcfg .= ' refid ';
1621
			$ntpcfg .= $config['ntpd']['gps']['refid'];
1622
		}
1623
		$ntpcfg .= "\n";
1624
	}elseif (is_array($config['ntpd']) && !empty($config['ntpd']['gpsport'])
1625
		&& file_exists('/dev/'.$config['ntpd']['gpsport'])
1626
		&& system_ntp_setup_gps($config['ntpd']['gpsport'])) {
1627
		/* This handles a 2.1 and earlier config */
1628
		$ntpcfg .= "# GPS Setup\n";
1629
		$ntpcfg .= "server 127.127.20.0 mode 0 minpoll 4 maxpoll 4 prefer\n";
1630
		$ntpcfg .= "fudge 127.127.20.0 time1 0.155 time2 0.000 flag1 1 flag2 0 flag3 1\n";
1631
		// Fall back to local clock if GPS is out of sync?
1632
		$ntpcfg .= "server 127.127.1.0\n";
1633
		$ntpcfg .= "fudge 127.127.1.0 stratum 12\n";
1634
	}
1635
	/* End GPS configuration */
1636
	
1637
	$ntpcfg .= "\n\n# Upstream Servers\n";
1638
	/* foreach through ntp servers and write out to ntpd.conf */
1639
	foreach (explode(' ', $config['system']['timeservers']) as $ts) {
1640
		$ntpcfg .= "server {$ts} iburst maxpoll 9";
1641
		if (substr_count($config['ntpd']['prefer'], $ts)) $ntpcfg .= ' prefer';
1642
		if (substr_count($config['ntpd']['noselect'], $ts)) $ntpcfg .= ' noselect';
1643
		$ntpcfg .= "\n";
1644
	}
1645
	unset($ts);
1646

    
1647
	$ntpcfg .= "\n\n";
1648
	$ntpcfg .= "disable monitor\n"; //prevent NTP reflection attack, see https://forum.pfsense.org/index.php/topic,67189.msg389132.html#msg389132
1649
	if (!empty($config['ntpd']['clockstats']) || !empty($config['ntpd']['loopstats']) || !empty($config['ntpd']['peerstats'])) {
1650
		$ntpcfg .= "enable stats\n";
1651
		$ntpcfg .= 'statistics';
1652
		if (!empty($config['ntpd']['clockstats'])) {
1653
			$ntpcfg .= ' clockstats';
1654
		}
1655
		if (!empty($config['ntpd']['loopstats'])) {
1656
			$ntpcfg .= ' loopstats';
1657
		}
1658
		if (!empty($config['ntpd']['peerstats'])) {
1659
			$ntpcfg .= ' peerstats';
1660
		}
1661
		$ntpcfg .= "\n";
1662
	}
1663
	$ntpcfg .= "statsdir {$statsdir}\n";
1664
	$ntpcfg .= 'logconfig =syncall +clockall';
1665
	if (!empty($config['ntpd']['logpeer'])) {
1666
		$ntpcfg .= ' +peerall';
1667
	}
1668
	if (!empty($config['ntpd']['logsys'])) {
1669
		$ntpcfg .= ' +sysall';
1670
	}
1671
	$ntpcfg .= "\n";
1672
	$ntpcfg .= "driftfile {$driftfile}\n";
1673
	/* Access restrictions */
1674
	$ntpcfg .= 'restrict default';
1675
	if (empty($config['ntpd']['kod'])) { /*note: this one works backwards */
1676
		$ntpcfg .= ' kod limited'; 
1677
	}
1678
	if (empty($config['ntpd']['nomodify'])) { /*note: this one works backwards */
1679
		$ntpcfg .= ' nomodify'; 
1680
	}
1681
	if (!empty($config['ntpd']['noquery'])) {
1682
		$ntpcfg .= ' noquery';
1683
	}
1684
	if (empty($config['ntpd']['nopeer'])) { /*note: this one works backwards */
1685
		$ntpcfg .= ' nopeer'; 
1686
	}
1687
	if (empty($config['ntpd']['notrap'])) { /*note: this one works backwards */
1688
		$ntpcfg .= ' notrap'; 
1689
	}
1690
	if (!empty($config['ntpd']['noserve'])) {
1691
		$ntpcfg .= ' noserve';
1692
	}
1693
	$ntpcfg .= "\nrestrict -6 default";
1694
	if (empty($config['ntpd']['kod'])) { /*note: this one works backwards */
1695
		$ntpcfg .= ' kod limited'; 
1696
	}
1697
	if (empty($config['ntpd']['nomodify'])) { /*note: this one works backwards */
1698
		$ntpcfg .= ' nomodify'; 
1699
	}
1700
	if (!empty($config['ntpd']['noquery'])) {
1701
		$ntpcfg .= ' noquery';
1702
	}
1703
	if (empty($config['ntpd']['nopeer'])) { /*note: this one works backwards */
1704
		$ntpcfg .= ' nopeer'; 
1705
	}
1706
	if (!empty($config['ntpd']['noserve'])) {
1707
		$ntpcfg .= ' noserve';
1708
	}
1709
	if (empty($config['ntpd']['notrap'])) { /*note: this one works backwards */
1710
		$ntpcfg .= ' notrap'; 
1711
	}
1712
	$ntpcfg .= "\n";
1713

    
1714
	/* A leapseconds file is really only useful if this clock is stratum 1 */
1715
	$ntpcfg .= "\n";
1716
	if (!empty($config['ntpd']['leapsec'])) {
1717
		$leapsec .= base64_decode($config['ntpd']['leapsec']);
1718
		file_put_contents('/var/db/leap-seconds', $leapsec);
1719
		$ntpcfg .= "leapfile /var/db/leap-seconds\n";
1720
	}
1721
	
1722

    
1723
	if (empty($config['ntpd']['interface'])) {
1724
		if (is_array($config['installedpackages']['openntpd']) && !empty($config['installedpackages']['openntpd']['config'][0]['interface']))
1725
			$interfaces = explode(",", $config['installedpackages']['openntpd']['config'][0]['interface']);
1726
		else
1727
			$interfaces = array();
1728
	} else
1729
		$interfaces = explode(",", $config['ntpd']['interface']);
1730

    
1731
	if (is_array($interfaces) && count($interfaces)) {
1732
		$ntpcfg .= "interface ignore all\n";
1733
		foreach ($interfaces as $interface) {
1734
			if (!is_ipaddr($interface)) {
1735
				$interface = get_real_interface($interface);
1736
			}
1737
			if (!empty($interface))
1738
				$ntpcfg .= "interface listen {$interface}\n";
1739
		}
1740
	}
1741

    
1742
	/* open configuration for writing or bail */
1743
	if (!@file_put_contents("{$g['varetc_path']}/ntpd.conf", $ntpcfg)) {
1744
		log_error("Could not open {$g['varetc_path']}/ntpd.conf for writing");
1745
		return;
1746
	}
1747

    
1748
	/* At bootup we just want to write out the config. */
1749
	if (!$start_ntpd)
1750
		return;
1751

    
1752
	/* if ntpd is running, kill it */
1753
	while (isvalidpid("{$g['varrun_path']}/ntpd.pid")) {
1754
		killbypid("{$g['varrun_path']}/ntpd.pid");
1755
	}
1756
	@unlink("{$g['varrun_path']}/ntpd.pid");
1757

    
1758
	/* if /var/empty does not exist, create it */
1759
	if(!is_dir("/var/empty"))
1760
		mkdir("/var/empty", 0775, true);
1761

    
1762
	/* start opentpd, set time now and use /var/etc/ntpd.conf */
1763
	mwexec("/usr/local/sbin/ntpd -g -c {$g['varetc_path']}/ntpd.conf -p {$g['varrun_path']}/ntpd.pid", false, true);
1764
	
1765
	// Note that we are starting up
1766
	log_error("NTPD is starting up.");
1767
	return;
1768
}
1769

    
1770
function sync_system_time() {
1771
	global $config, $g;
1772

    
1773
	if (platform_booting())
1774
		echo gettext("Syncing system time before startup...");
1775

    
1776
	/* foreach through servers and write out to ntpd.conf */
1777
	foreach (explode(' ', $config['system']['timeservers']) as $ts) {
1778
		mwexec("/usr/local/sbin/ntpdate -s $ts");
1779
	}
1780
	
1781
	if (platform_booting())
1782
		echo gettext("done.") . "\n";
1783
	
1784
}
1785

    
1786
function system_halt() {
1787
	global $g;
1788

    
1789
	system_reboot_cleanup();
1790

    
1791
	mwexec("/usr/bin/nohup /etc/rc.halt > /dev/null 2>&1 &");
1792
}
1793

    
1794
function system_reboot() {
1795
	global $g;
1796

    
1797
	system_reboot_cleanup();
1798

    
1799
	mwexec("nohup /etc/rc.reboot > /dev/null 2>&1 &");
1800
}
1801

    
1802
function system_reboot_sync() {
1803
	global $g;
1804

    
1805
	system_reboot_cleanup();
1806

    
1807
	mwexec("/etc/rc.reboot > /dev/null 2>&1");
1808
}
1809

    
1810
function system_reboot_cleanup() {
1811
	global $config, $cpzone;
1812

    
1813
	mwexec("/usr/local/bin/beep.sh stop");
1814
	require_once("captiveportal.inc");
1815
	if (is_array($config['captiveportal'])) {
1816
		foreach ($config['captiveportal'] as $cpzone=>$cp) {
1817
			captiveportal_radius_stop_all();
1818
			captiveportal_send_server_accounting(true);
1819
		}
1820
	}
1821
	require_once("voucher.inc");
1822
	voucher_save_db_to_config();
1823
	require_once("pkg-utils.inc");
1824
	stop_packages();
1825
}
1826

    
1827
function system_do_shell_commands($early = 0) {
1828
	global $config, $g;
1829
	if(isset($config['system']['developerspew'])) {
1830
		$mt = microtime();
1831
		echo "system_do_shell_commands() being called $mt\n";
1832
	}
1833

    
1834
	if ($early)
1835
		$cmdn = "earlyshellcmd";
1836
	else
1837
		$cmdn = "shellcmd";
1838

    
1839
	if (is_array($config['system'][$cmdn])) {
1840

    
1841
		/* *cmd is an array, loop through */
1842
		foreach ($config['system'][$cmdn] as $cmd) {
1843
			exec($cmd);
1844
		}
1845

    
1846
	} elseif($config['system'][$cmdn] <> "") {
1847

    
1848
		/* execute single item */
1849
		exec($config['system'][$cmdn]);
1850

    
1851
	}
1852
}
1853

    
1854
function system_console_configure() {
1855
	global $config, $g;
1856
	if(isset($config['system']['developerspew'])) {
1857
		$mt = microtime();
1858
		echo "system_console_configure() being called $mt\n";
1859
	}
1860

    
1861
	if (isset($config['system']['disableconsolemenu'])) {
1862
		touch("{$g['varetc_path']}/disableconsole");
1863
	} else {
1864
		unlink_if_exists("{$g['varetc_path']}/disableconsole");
1865
	}
1866
}
1867

    
1868
function system_dmesg_save() {
1869
	global $g;
1870
	if(isset($config['system']['developerspew'])) {
1871
		$mt = microtime();
1872
		echo "system_dmesg_save() being called $mt\n";
1873
	}
1874

    
1875
	$dmesg = "";
1876
	$_gb = exec("/sbin/dmesg", $dmesg);
1877

    
1878
	/* find last copyright line (output from previous boots may be present) */
1879
	$lastcpline = 0;
1880

    
1881
	for ($i = 0; $i < count($dmesg); $i++) {
1882
		if (strstr($dmesg[$i], "Copyright (c) 1992-"))
1883
			$lastcpline = $i;
1884
	}
1885

    
1886
	$fd = fopen("{$g['varlog_path']}/dmesg.boot", "w");
1887
	if (!$fd) {
1888
		printf(gettext("Error: cannot open dmesg.boot in system_dmesg_save().%s"), "\n");
1889
		return 1;
1890
	}
1891

    
1892
	for ($i = $lastcpline; $i < count($dmesg); $i++)
1893
		fwrite($fd, $dmesg[$i] . "\n");
1894

    
1895
	fclose($fd);
1896
	unset($dmesg);
1897

    
1898
	return 0;
1899
}
1900

    
1901
function system_set_harddisk_standby() {
1902
	global $g, $config;
1903
	if(isset($config['system']['developerspew'])) {
1904
		$mt = microtime();
1905
		echo "system_set_harddisk_standby() being called $mt\n";
1906
	}
1907

    
1908
	if (isset($config['system']['harddiskstandby'])) {
1909
		if (platform_booting()) {
1910
			echo gettext('Setting hard disk standby... ');
1911
		}
1912

    
1913
		$standby = $config['system']['harddiskstandby'];
1914
		// Check for a numeric value
1915
		if (is_numeric($standby)) {
1916
			// Sync the disk(s)
1917
			pfSense_sync();
1918
			if (set_single_sysctl('hw.ata.standby', (int)$standby)) {
1919
				// Reinitialize ATA-drives
1920
				mwexec('/usr/local/sbin/atareinit');
1921
				if (platform_booting()) {
1922
					echo gettext("done.") . "\n";
1923
				}
1924
			} else if (platform_booting()) {
1925
				echo gettext("failed!") . "\n";
1926
			}
1927
		} else if (platform_booting()) {
1928
			echo gettext("failed!") . "\n";
1929
		}
1930
	}
1931
}
1932

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

    
1940
	activate_sysctls();	
1941

    
1942
	if (isset($config['system']['sharednet'])) {
1943
		system_disable_arp_wrong_if();
1944
	}
1945
}
1946

    
1947
function system_disable_arp_wrong_if() {
1948
	global $config;
1949
	if(isset($config['system']['developerspew'])) {
1950
		$mt = microtime();
1951
		echo "system_disable_arp_wrong_if() being called $mt\n";
1952
	}
1953
	set_sysctl(array(
1954
		"net.link.ether.inet.log_arp_wrong_iface" => "0",
1955
		"net.link.ether.inet.log_arp_movements" => "0"
1956
	));
1957
}
1958

    
1959
function system_enable_arp_wrong_if() {
1960
	global $config;
1961
	if(isset($config['system']['developerspew'])) {
1962
		$mt = microtime();
1963
		echo "system_enable_arp_wrong_if() being called $mt\n";
1964
	}
1965
	set_sysctl(array(
1966
		"net.link.ether.inet.log_arp_wrong_iface" => "1",
1967
		"net.link.ether.inet.log_arp_movements" => "1"
1968
	));
1969
}
1970

    
1971
function enable_watchdog() {
1972
	global $config;
1973
	return;
1974
	$install_watchdog = false;
1975
	$supported_watchdogs = array("Geode");
1976
	$file = file_get_contents("/var/log/dmesg.boot");
1977
	foreach($supported_watchdogs as $sd) {
1978
		if(stristr($file, "Geode")) {
1979
			$install_watchdog = true;
1980
		}
1981
	}
1982
	if($install_watchdog == true) {
1983
		if(is_process_running("watchdogd"))
1984
			mwexec("/usr/bin/killall watchdogd", true);
1985
		exec("/usr/sbin/watchdogd");
1986
	}
1987
}
1988

    
1989
function system_check_reset_button() {
1990
	global $g;
1991

    
1992
	$specplatform = system_identify_specific_platform();
1993

    
1994
	switch ($specplatform['name']) {
1995
	case 'alix':
1996
	case 'wrap':
1997
	case 'FW7541':
1998
	case 'APU':
1999
	case 'C2358':
2000
		break;
2001
	default:
2002
		return 0;
2003
	}
2004

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

    
2007
	if ($retval == 99) {
2008
		/* user has pressed reset button for 2 seconds - 
2009
		   reset to factory defaults */
2010
		echo <<<EOD
2011

    
2012
***********************************************************************
2013
* Reset button pressed - resetting configuration to factory defaults. *
2014
* The system will reboot after this completes.                        *
2015
***********************************************************************
2016

    
2017

    
2018
EOD;
2019
		
2020
		reset_factory_defaults();
2021
		system_reboot_sync();
2022
		exit(0);
2023
	}
2024

    
2025
	return 0;
2026
}
2027

    
2028
/* attempt to identify the specific platform (for embedded systems)
2029
   Returns an array with two elements:
2030
	name => platform string (e.g. 'wrap', 'alix' etc.)
2031
	descr => human-readable description (e.g. "PC Engines WRAP")
2032
*/
2033
function system_identify_specific_platform() {
2034
	global $g;
2035
	
2036
	if ($g['platform'] == 'generic-pc')
2037
		return array('name' => 'generic-pc', 'descr' => gettext("Generic PC"));
2038
	
2039
	if ($g['platform'] == 'generic-pc-cdrom')
2040
		return array('name' => 'generic-pc-cdrom', 'descr' => gettext("Generic PC (CD-ROM)"));
2041
	
2042
	/* Try to guess from smbios strings */
2043
	unset($output);
2044
	$_gb = exec('/bin/kenv smbios.system.product 2>/dev/null', $output);
2045
	switch ($output[0]) {
2046
	case 'FW7541':
2047
		return (array('name' => 'FW7541', 'descr' => 'Netgate FW7541'));
2048
		break;
2049
	case 'APU':
2050
		return (array('name' => 'APU', 'descr' => 'Netgate APU'));
2051
		break;
2052
	case 'RCC-VE':
2053
		return (array('name' => 'C2358', 'descr' => 'Netgate C2358'));
2054
		break;
2055
	}
2056

    
2057
	/* the rest of the code only deals with 'embedded' platforms */
2058
	if ($g['platform'] != 'nanobsd')
2059
		return array('name' => $g['platform'], 'descr' => $g['platform']);
2060

    
2061
	$dmesg = get_single_sysctl('hw.model');
2062

    
2063
	if (strpos($dmesg, "PC Engines WRAP") !== false)
2064
		return array('name' => 'wrap', 'descr' => gettext('PC Engines WRAP'));
2065
	
2066
	if (strpos($dmesg, "PC Engines ALIX") !== false)
2067
		return array('name' => 'alix', 'descr' => gettext('PC Engines ALIX'));
2068

    
2069
	if (preg_match("/Soekris net45../", $dmesg, $matches))
2070
		return array('name' => 'net45xx', 'descr' => $matches[0]);
2071
	
2072
	if (preg_match("/Soekris net48../", $dmesg, $matches))
2073
		return array('name' => 'net48xx', 'descr' => $matches[0]);
2074
		
2075
	if (preg_match("/Soekris net55../", $dmesg, $matches))
2076
		return array('name' => 'net55xx', 'descr' => $matches[0]);
2077

    
2078
	unset($dmesg);
2079

    
2080
	$dmesg_boot = system_get_dmesg_boot();
2081
	if (strpos($dmesg_boot, "PC Engines ALIX") !== false)
2082
		return array('name' => 'alix', 'descr' => gettext('PC Engines ALIX'));
2083
	unset($dmesg_boot);
2084

    
2085
	/* unknown embedded platform */
2086
	return array('name' => 'embedded', 'descr' => gettext('embedded (unknown)'));
2087
}
2088

    
2089
function system_get_dmesg_boot() {
2090
	global $g;
2091
		
2092
	return file_get_contents("{$g['varlog_path']}/dmesg.boot");
2093
}
2094

    
2095
function get_possible_listen_ips($include_ipv6_link_local=false) {
2096
	$interfaces = get_configured_interface_with_descr();
2097
	$carplist = get_configured_carp_interface_list();
2098
	$listenips = array();
2099
	foreach ($carplist as $cif => $carpip)
2100
		$interfaces[$cif] = $carpip." (".get_vip_descr($carpip).")";
2101
	$aliaslist = get_configured_ip_aliases_list();
2102
	foreach ($aliaslist as $aliasip => $aliasif)
2103
		$interfaces[$aliasip] = $aliasip." (".get_vip_descr($aliasip).")";
2104
	foreach ($interfaces as $iface => $ifacename) {
2105
		$tmp["name"]  = $ifacename;
2106
		$tmp["value"] = $iface;
2107
		$listenips[] = $tmp;
2108
		if ($include_ipv6_link_local) {
2109
			$llip = find_interface_ipv6_ll(get_real_interface($iface));
2110
			if (!empty($llip)) {
2111
				$tmp["name"]  = "{$ifacename} IPv6 Link-Local";
2112
				$tmp["value"] = $llip;
2113
				$listenips[] = $tmp;
2114
			}
2115
		}
2116
	}
2117
	$tmp["name"]  = "Localhost";
2118
	$tmp["value"] = "lo0";
2119
	$listenips[] = $tmp;
2120
	return $listenips;
2121
}
2122

    
2123
function get_possible_traffic_source_addresses($include_ipv6_link_local=false) {
2124
	global $config;
2125
	$sourceips = get_possible_listen_ips($include_ipv6_link_local);
2126
	foreach (array('server', 'client') as $mode) {
2127
		if (is_array($config['openvpn']["openvpn-{$mode}"])) {
2128
			foreach ($config['openvpn']["openvpn-{$mode}"] as $id => $setting) {
2129
				if (!isset($setting['disable'])) {
2130
					$vpn = array();
2131
					$vpn['value'] = 'ovpn' . substr($mode, 0, 1) . $setting['vpnid'];
2132
					$vpn['name'] = gettext("OpenVPN") . " ".$mode.": ".htmlspecialchars($setting['description']);
2133
					$sourceips[] = $vpn;
2134
				}
2135
			}
2136
		}
2137
	}
2138
	return $sourceips;
2139
}
2140
?>
(53-53/68)