Project

General

Profile

Download (33.3 KB) Statistics
| Branch: | Tag: | Revision:
1
<?php
2
/* $Id$ */
3
/*
4
	services.inc
5
	part of the pfSense project (http://www.pfsense.com)
6

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

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

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

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

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

    
33
/*
34
	pfSense_BUILDER_BINARIES:	/usr/bin/killall	/bin/sh	/usr/local/sbin/dhcpd	/usr/local/sbin/igmpproxy
35
	pfSense_BUILDER_BINARIES:	/sbin/ifconfig	/usr/sbin/arp	/sbin/ifconfig	/usr/local/sbin/dnsmasq
36
	pfSense_BUILDER_BINARIES:	/usr/sbin/bsnmpd	/sbin/route	/usr/local/sbin/olsrd
37
	pfSense_BUILDER_BINARIES:	/usr/local/sbin/miniupnpd	
38
	pfSense_MODULE:	utils
39
*/
40

    
41
function services_parse_dhcpd_hostnames() {
42
	$ps = `ps awux | grep isc | grep -v grep | grep parse | awk '{ print $2 }'`;
43
	if($ps)
44
		exec("kill {$ps}");
45
	// Launch if option enabled
46
	if (isset($config['dnsmasq']['regdhcp'])) {
47
		mwexec_bg("sh /etc/rc.parse-isc-dhcpd");
48
	}
49
}
50

    
51
function services_dhcpd_configure() {
52
	global $config, $g;
53
	
54
	if($g['services_dhcp_server_enable'] == false) 
55
		return;
56

    
57
	if(isset($config['system']['developerspew'])) {
58
		$mt = microtime();
59
		echo "services_dhcpd_configure($if) being called $mt\n";
60
	}
61
	
62
	/* kill any running dhcpd */
63
	if(is_process_running("dhcpd"))
64
		mwexec("killall dhcpd", true);
65

    
66
	/* DHCP enabled on any interfaces? */
67
	if (!is_dhcp_server_enabled())
68
		return 0;
69

    
70
	/* if OLSRD is enabled, allow WAN to house DHCP. */
71
	if($config['installedpackages']['olsrd'])
72
		foreach($config['installedpackages']['olsrd']['config'] as $olsrd)
73
				if($olsrd['enable'])
74
					$is_olsr_enabled = true;
75

    
76
	/* configure DHCPD chroot */
77
	$fd = fopen("/tmp/dhcpd.sh","w");
78
	$status = `mount | grep "{$g['dhcpd_chroot_path']}/dev"`;
79
	fwrite($fd, "mkdir -p {$g['dhcpd_chroot_path']}\n");
80
	fwrite($fd, "mkdir -p {$g['dhcpd_chroot_path']}/dev\n");
81
	fwrite($fd, "mkdir -p {$g['dhcpd_chroot_path']}/etc\n");
82
	fwrite($fd, "mkdir -p {$g['dhcpd_chroot_path']}/usr/local/sbin\n");
83
	fwrite($fd, "mkdir -p {$g['dhcpd_chroot_path']}/var/db\n");
84
	fwrite($fd, "mkdir -p {$g['dhcpd_chroot_path']}/var/run\n");	
85
	fwrite($fd, "mkdir -p {$g['dhcpd_chroot_path']}/usr\n");
86
	fwrite($fd, "mkdir -p {$g['dhcpd_chroot_path']}/lib\n");
87
	fwrite($fd, "mkdir -p {$g['dhcpd_chroot_path']}/run\n");
88
	fwrite($fd, "chown -R dhcpd:_dhcp {$g['dhcpd_chroot_path']}/*\n");
89
	fwrite($fd, "cp /lib/libc.so.* {$g['dhcpd_chroot_path']}/lib/\n");
90
	fwrite($fd, "cp /usr/local/sbin/dhcpd {$g['dhcpd_chroot_path']}/usr/local/sbin/\n");
91
	fwrite($fd, "chmod a+rx {$g['dhcpd_chroot_path']}/usr/local/sbin/dhcpd\n");
92
	if(!trim($status))
93
		fwrite($fd, "mount -t devfs devfs {$g['dhcpd_chroot_path']}/dev\n");
94
	fclose($fd);
95
	mwexec("/bin/sh /tmp/dhcpd.sh");
96

    
97
	$syscfg = $config['system'];
98
	$dhcpdcfg = $config['dhcpd'];
99
	$Iflist = get_configured_interface_list();
100
		
101
	if ($g['booting'])
102
		echo "Starting DHCP service...";
103
	else
104
		sleep(1);
105

    
106
	/* write dhcpd.conf */
107
	$fd = fopen("{$g['dhcpd_chroot_path']}/etc/dhcpd.conf", "w");
108
	if (!$fd) {
109
		printf("Error: cannot open dhcpd.conf in services_dhcpd_configure().\n");
110
		return 1;
111
	}
112

    
113
	$optcounter = 0;
114
	$custoptions = "";
115
	foreach ($dhcpdcfg as $dhcpif => $dhcpifconf) {	
116
		if($dhcpifconf['numberoptions']['item']) {
117
			foreach($dhcpifconf['numberoptions']['item'] as $item) {
118
				$custoptions .= "option custom-opt-$optcounter code {$item['number']} = text;\n";
119
				$optcounter++;
120
			}
121
		}
122
	}
123

    
124
	$dhcpdconf = <<<EOD
125
	
126
option domain-name "{$syscfg['domain']}";
127
option ldap-server code 95 = text;
128
option domain-search-list code 119 = text;
129
{$custoptions}
130
default-lease-time 7200;
131
max-lease-time 86400;
132
log-facility local7;
133
ddns-update-style none;
134
one-lease-per-client true;
135
deny duplicates;
136
ping-check true;
137

    
138
EOD;
139

    
140
	if(isset($dhcpifconf['alwaysbroadcast'])) 
141
		$dhcpdconf .= "always-broadcast on\n";
142

    
143
	$dhcpdifs = array();
144

    
145
	/*    loop through and determine if we need to setup
146
	 *    failover peer "bleh" entries
147
	 */
148
	$dhcpnum = 0;
149
	foreach ($dhcpdcfg as $dhcpif => $dhcpifconf) {
150

    
151
		if (!isset($dhcpifconf['enable']))
152
			continue;
153

    
154
		if(!isset($dhcpifconf['disableauthoritative']))
155
			$dhcpdconf .= "authoritative;\n";
156

    
157
		if($dhcpifconf['failover_peerip'] <> "") {
158
			/*
159
			 *    yep, failover peer is defined.
160
			 *    does it match up to a defined vip?
161
			 */
162
			$skew = 110;
163
			$a_vip = &$config['virtualip']['vip'];
164
			if(is_array($a_vip)) {
165
				foreach ($a_vip as $vipent) {
166
					$int = guess_interface_from_ip($dhcpifconf['failover_peerip']);
167
					$intip = find_interface_ip($int);
168
					$real_dhcpif = convert_friendly_interface_to_real_interface_name($dhcpif);
169
					if($int == $real_dhcpif) {
170
						/* this is the interface! */
171
						if($vipent['advskew'] < "20")
172
							$skew = 0;
173
					}
174
				}
175
			} else {
176
				log_error("Warning!  DHCP Failover setup and no CARP virtual IP's defined!");
177
			}
178
			if($skew > 10) {
179
				$type = "secondary";
180
				$dhcpdconf_pri  = "mclt 600;\n";
181
				$my_port = "520";
182
				$peer_port = "519";
183
			} else {
184
				$my_port = "519";
185
				$peer_port = "520";
186
				$type = "primary";
187
				$dhcpdconf_pri  = "split 128;\n";
188
				$dhcpdconf_pri .= "  mclt 600;\n";
189
			}
190
			$dhcpdconf .= <<<EOPP
191
failover peer "dhcp{$dhcpnum}" {
192
  {$type};
193
  address {$intip};
194
  port {$my_port};
195
  peer address {$dhcpifconf['failover_peerip']};
196
  peer port {$peer_port};
197
  max-response-delay 10;
198
  max-unacked-updates 10;
199
  {$dhcpdconf_pri}
200
  load balance max seconds 3;
201
}
202

    
203
EOPP;
204
		$dhcpnum++;
205
		}
206
	}
207

    
208
	$dhcpnum = 0;
209

    
210
	foreach ($dhcpdcfg as $dhcpif => $dhcpifconf) {
211

    
212
		$ifcfg = $config['interfaces'][$dhcpif];
213

    
214
		if (!isset($dhcpifconf['enable']) || !isset($Iflist[$dhcpif]))
215
			continue;
216
		$ifcfgip = get_interface_ip($dhcpif);
217
		$ifcfgsn = get_interface_subnet($dhcpif);
218
		$subnet = gen_subnet($ifcfgip, $ifcfgsn);
219
		$subnetmask = gen_subnet_mask($ifcfgsn);
220

    
221
		if($is_olsr_enabled == true)
222
			if($dhcpifconf['netmask'])
223
				$subnetmask = gen_subnet_mask($dhcpifconf['netmask']);
224

    
225
		$dnscfg = "";
226

    
227
		if ($dhcpifconf['domain']) {
228
			$dnscfg .= "	option domain-name \"{$dhcpifconf['domain']}\";\n";
229
		}
230
		
231
    		if($dhcpifconf['domainsearchlist'] <> "") {
232
			$dnscfg .= "	option domain-search-list \"{$dhcpifconf['domainsearchlist']}\";\n";
233
    		}
234

    
235
		if (isset($dhcpifconf['ddnsupdate'])) {
236
			if($dhcpifconf['ddnsdomain'] <> "") {
237
				$dnscfg .= "	ddns-domainname \"{$dhcpifconf['ddnsdomain']}\";\n";
238
			}
239
			$dnscfg .= "	ddns-update-style interim;\n";
240
		}
241

    
242
		if (is_array($dhcpifconf['dnsserver']) && ($dhcpifconf['dnsserver'][0])) {
243
			$dnscfg .= "	option domain-name-servers " . join(",", $dhcpifconf['dnsserver']) . ";";
244
		} else if (isset($config['dnsmasq']['enable'])) {
245
			$dnscfg .= "	option domain-name-servers {$ifcfgip};";
246
		} else if (is_array($syscfg['dnsserver']) && ($syscfg['dnsserver'][0])) {
247
			$dnscfg .= "	option domain-name-servers " . join(",", $syscfg['dnsserver']) . ";";
248
		}
249

    
250
		$dhcpdconf .= "subnet $subnet netmask $subnetmask {\n";
251
		$dhcpdconf .= "	pool {\n";
252

    
253
		/* is failover dns setup? */
254
		if (is_array($dhcpifconf['dnsserver']) && $dhcpifconf['dnsserver'][0] <> "") {
255
			$dhcpdconf .= "		option domain-name-servers {$dhcpifconf['dnsserver'][0]}";
256
			if($dhcpifconf['dnsserver'][1] <> "")
257
				$dhcpdconf .= ",{$dhcpifconf['dnsserver'][1]}";
258
			$dhcpdconf .= ";\n";
259
		}
260

    
261
		if($dhcpifconf['failover_peerip'] <> "")
262
			$dhcpdconf .= "		deny dynamic bootp clients;\n";
263

    
264
		if (isset($dhcpifconf['denyunknown']))
265
		   $dhcpdconf .= "		deny unknown clients;\n";
266

    
267
		if ($dhcpifconf['gateway'])
268
			$routers = $dhcpifconf['gateway'];
269
		else
270
			$routers = $ifcfgip;
271

    
272
		if($dhcpifconf['failover_peerip'] <> "") {
273
			$dhcpdconf .= "		failover peer \"dhcp{$dhcpnum}\";\n";
274
			$dhcpnum++;
275
		}
276

    
277
		$dhcpdconf .= <<<EOD
278
		range {$dhcpifconf['range']['from']} {$dhcpifconf['range']['to']};
279
	}
280
	option routers {$routers};
281
$dnscfg
282

    
283
EOD;
284
    
285
		// default-lease-time
286
		if ($dhcpifconf['defaultleasetime'])
287
			$dhcpdconf .= "	default-lease-time {$dhcpifconf['defaultleasetime']};\n";
288

    
289
		// max-lease-time
290
		if ($dhcpifconf['maxleasetime'])
291
			$dhcpdconf .= "	max-lease-time {$dhcpifconf['maxleasetime']};\n";
292

    
293
		// netbios-name*
294
		if (is_array($dhcpifconf['winsserver']) && $dhcpifconf['winsserver'][0]) {
295
			$dhcpdconf .= "	option netbios-name-servers " . join(",", $dhcpifconf['winsserver']) . ";\n";
296
			$dhcpdconf .= "	option netbios-node-type 8;\n";
297
		}
298

    
299
		// ntp-servers
300
		if (is_array($dhcpifconf['ntpserver']) && $dhcpifconf['ntpserver'][0])
301
			$dhcpdconf .= "	option ntp-servers " . join(",", $dhcpifconf['ntpserver']) . ";\n";
302

    
303
		// tftp-server-name
304
		if ($dhcpifconf['tftp'] <> "")
305
			$dhcpdconf .= "	option tftp-server-name \"{$dhcpifconf['tftp']}\";\n";
306

    
307
		// Handle option, number rowhelper values
308
		$optcounter = 0;
309
		$dhcpdconf .= "\n";
310
		if($dhcpifconf['numberoptions']['item']) {
311
			foreach($dhcpifconf['numberoptions']['item'] as $item) {
312
				$dhcpdconf .= "	option custom-opt-$optcounter \"{$item['value']}\";\n";
313
				$optcounter++;
314
			}
315
		}
316

    
317
		// ldap-server
318
		if ($dhcpifconf['ldap'] <> "")
319
			$dhcpdconf .= "	option ldap-server \"{$dhcpifconf['ldap']}\";\n";
320

    
321
		// net boot information
322
		if(isset($dhcpifconf['netboot'])) {
323
			if (($dhcpifconf['next-server'] <> "") && ($dhcpifconf['filename'] <> "")) {
324
				$dhcpdconf .= "	next-server {$dhcpifconf['next-server']};\n";
325
				$dhcpdconf .= "	filename \"{$dhcpifconf['filename']}\";\n";
326
			}
327
			if ($dhcpifconf['rootpath'] <> "") {
328
				$dhcpdconf .= "	option root-path \"{$dhcpifconf['rootpath']}\";\n";
329
      		}
330
		}
331
		
332
		$dhcpdconf .= <<<EOD
333
}
334

    
335
EOD;
336

    
337
		/* add static mappings */
338
		if (is_array($dhcpifconf['staticmap'])) {
339

    
340
			$i = 0;
341
			foreach ($dhcpifconf['staticmap'] as $sm) {
342
				$dhcpdconf .= <<<EOD
343
host s_{$dhcpif}_{$i} {
344
	hardware ethernet {$sm['mac']};
345

    
346
EOD;
347
				if ($sm['ipaddr'])
348
					$dhcpdconf .= "	fixed-address {$sm['ipaddr']};\n";
349

    
350
				if ($sm['hostname']) {
351
					$dhhostname = str_replace(" ", "_", $sm['hostname']);
352
					$dhhostname = str_replace(".", "_", $dhhostname);
353
					$dhcpdconf .= "	option host-name {$dhhostname};\n";
354
				}
355

    
356
				$dhcpdconf .= "}\n";
357
				$i++;
358
			}
359
		}
360

    
361
		$dhcpdifs[] = get_real_interface($dhcpif);
362
	}
363

    
364
	fwrite($fd, $dhcpdconf);
365
	fclose($fd);
366

    
367
	/* create an empty leases database */
368
	touch("{$g['dhcpd_chroot_path']}/var/db/dhcpd.leases");
369
	touch("{$g['varrun_path']}/dhcpd.pid");
370
	
371

    
372
	/* fire up dhcpd in a chroot */
373
	mwexec("/usr/local/sbin/dhcpd -user dhcpd -group _dhcp -chroot {$g['dhcpd_chroot_path']} -cf {$g['dhcpd_chroot_path']}/etc/dhcpd.conf " .
374
		join(" ", $dhcpdifs));
375

    
376
	if ($g['booting']) {
377
		print "done.\n";
378
	}
379

    
380
	return 0;
381
}
382

    
383
function services_igmpproxy_configure() {
384
        global $config, $g;
385

    
386
        $iflist = get_configured_interface_list();
387

    
388
        /* kill any running igmpproxy */
389
        killbyname("igmpproxy");
390

    
391
	if (!is_array($config['igmpproxy']['igmpentry']))
392
		return 1;
393

    
394
        $igmpconf = <<<EOD
395

    
396
##------------------------------------------------------
397
## Enable Quickleave mode (Sends Leave instantly)
398
##------------------------------------------------------
399
quickleave
400

    
401
EOD;
402

    
403
        foreach ($config['igmpproxy']['igmpentry'] as $igmpcf) {
404
                unset($iflist[$igmpcf['ifname']]);
405
                $realif = get_real_interface($igmpcf['ifname']);
406
                if (empty($igmpcf['threshold']))
407
                        $threshld = 1;
408
                else
409
                        $threshld = $igmpcf['threshold'];
410
                $igmpconf .= "phyint {$realif} {$igmpcf['type']} ratelimit 0 threshold {$threshld}\n";
411

    
412
                if ($igmpcf['address'] <> "") {
413
                        $item = explode(" ", $igmpcf['address']);
414
                        foreach($item as $iww)
415
                                $igmpconf .= "altnet {$iww}\n";
416
                }
417
                $igmpconf .= "\n";
418
        }
419
        foreach ($iflist as $ifn) {
420
                $realif = get_real_interface($ifn);
421
                $igmpconf .= "phyint {$realif} disabled\n";
422
        }
423

    
424
        $igmpfl = fopen($g['tmp_path'] . "/igmpproxy.conf", "w");
425
        if (!$igmpfl) {
426
                log_error("Could not write Igmpproxy configuration file!");
427
                return;
428
        }
429
        fwrite($igmpfl, $igmpconf);
430
        fclose($igmpfl);
431

    
432
        mwexec("/usr/local/sbin/igmpproxy -c " . $g['tmp_path'] . "/igmpproxy.conf");
433
        log_error("Started Igmpproxy service sucsesfully.");
434

    
435
        return 0;
436
}
437

    
438
function interfaces_staticarp_configure($if) {
439
	global $config, $g;
440
	if(isset($config['system']['developerspew'])) {
441
		$mt = microtime();
442
		echo "interfaces_staticarp_configure($if) being called $mt\n";
443
	}
444

    
445
        $ifcfg = $config['interfaces'][$if];
446

    
447
        /* Enable staticarp, if enabled */
448
        if(isset($config['dhcpd'][$if]['staticarp'])) {
449
                mwexec("/sbin/ifconfig " . escapeshellarg($ifcfg['if']) . " staticarp " );
450
                mwexec("/usr/sbin/arp -ad > /dev/null 2>&1 ");
451
                if (is_array($config['dhcpd'][$if]['staticmap'])) {
452

    
453
                        foreach ($config['dhcpd'][$if]['staticmap'] as $arpent) {
454
                                mwexec("/usr/sbin/arp -s " . escapeshellarg($arpent['ipaddr']) . " " . escapeshellarg($arpent['mac']));
455

    
456
                        }
457

    
458
                }
459
        } else {
460
                mwexec("/sbin/ifconfig " . escapeshellarg($ifcfg['if']) . " -staticarp " );
461
                mwexec("/usr/sbin/arp -da > /dev/null 2>&1 ");
462
        }
463

    
464
        return 0;
465
}
466

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

    
474
	/* kill any running dhcrelay */
475
	killbypid("{$g['varrun_path']}/dhcrelay.pid");
476

    
477
	$dhcrelaycfg = $config['dhcrelay'];
478

    
479
	/* DHCPRelay enabled on any interfaces? */
480
	$dhcrelayenable = false;
481
	if(is_array($dhcrelaycfg)) {
482
		foreach ($dhcrelaycfg as $dhcrelayif => $dhcrelayifconf) {
483
			if (isset($dhcrelayifconf['enable']) &&
484
				(($dhcrelayif == "lan") ||
485
				(isset($config['interfaces'][$dhcrelayif]['enable']) &&
486
				$config['interfaces'][$dhcrelayif]['if'] && (!link_interface_to_bridge($dhcrelayif)))))
487
				$dhcrelayenable = true;
488
		}
489
	}
490

    
491
	if (!$dhcrelayenable)
492
		return 0;
493

    
494
	if ($g['booting'])
495
		echo "Starting DHCP relay service...";
496
	else
497
		sleep(1);
498

    
499
	$dhcrelayifs = array();
500
	foreach ($dhcrelaycfg as $dhcrelayif => $dhcrelayifconf) {
501

    
502
		$ifcfg = $config['interfaces'][$dhcrelayif];
503

    
504
		if (!isset($dhcrelayifconf['enable']) ||
505
			(($dhcrelayif != "lan") &&
506
			(!isset($ifcfg['enable']) || !$ifcfg['if'] || 
507
			link_interface_to_bridge($dhcrelayif))))
508
			continue;
509

    
510
		$dhcrelayifs[] = get_real_interface($dhcprelayif);
511
	}
512

    
513
	/* In order for the relay to work, it needs to be active on the
514
	   interface in which the destination server sits */
515
	$dhrelayifs = get_configured_interface_list();
516
	foreach ($dhrelayifs as $ifname) {
517
		$subnet = get_interface_ip($ifname) . "/" . get_interface_subnet($ifname);
518
		if (ip_in_subnet($dhcrelaycfg['server'],$subnet))
519
			$destif = $ifname['if'];
520
	}
521

    
522
	if (!isset($destif))
523
		$destif = $config['interfaces']['wan']['if'];
524

    
525
	$dhcrelayifs[] = $destif;
526
	$dhcrelayifs = array_unique($dhcrelayifs);
527

    
528
	/* fire up dhcrelay */
529
	$cmd = "/usr/local/sbin/dhcrelay -i " .  join(" -i ", $dhcrelayifs);
530

    
531
	if (isset($dhcrelaycfg['agentoption']))
532
		$cmd .=  " -a -m replace";
533

    
534
	$cmd .= " {$dhcrelaycfg['server']}";
535
	mwexec($cmd);
536

    
537
	return 0;
538
}
539

    
540
function services_dyndns_configure_client($conf) {
541

    
542
	/* load up the dyndns.class */
543
	require_once("dyndns.class");
544

    
545
	log_error("DynDns: Running updatedns()");
546

    
547
	$dns = new updatedns($dnsService = $conf['type'],
548
		$dnsHost = $conf['host'],
549
		$dnsUser = $conf['username'],
550
		$dnsPass = $conf['password'],
551
		$dnsWilcard = $conf['wildcard'],
552
		$dnsMX = $conf['mx'], 
553
		$dnsIf = "{$conf['interface']}");
554

    
555
}
556

    
557
function services_dyndns_configure($int = "") {
558
	global $config, $g;
559
	if(isset($config['system']['developerspew'])) {
560
		$mt = microtime();
561
		echo "services_dyndns_configure() being called $mt\n";
562
	}
563

    
564
	$dyndnscfg = $config['dyndnses']['dyndns'];
565

    
566
	if (is_array($dyndnscfg)) {
567
		if ($g['booting']) 
568
			echo "Starting DynDNS clients...";
569

    
570
		foreach ($dyndnscfg as $dyndns) {
571
			if (!isset($dyndns['enable']))
572
				continue;
573

    
574
			if (!empty($int) && $int != $dyndns['interface'])
575
				continue;
576

    
577
			services_dyndns_configure_client($dyndns);
578

    
579
			sleep(1);
580

    
581
			if (!empty($int))
582
				break;
583
		}
584

    
585
		if ($g['booting'])
586
			echo "done.\n";
587
	}
588

    
589
	return 0;
590
}
591

    
592
function services_dnsmasq_configure() {
593
	global $config, $g;
594
	$return = 0;
595
	
596
	if(isset($config['system']['developerspew'])) {
597
		$mt = microtime();
598
		echo "services_dnsmasq_configure() being called $mt\n";
599
	}
600

    
601
	/* kill any running dnsmasq */
602
	sigkillbypid("{$g['varrun_path']}/dnsmasq.pid", "TERM");
603

    
604
	if (isset($config['dnsmasq']['enable'])) {
605

    
606
		if ($g['booting'])
607
			echo "Starting DNS forwarder...";
608
		else
609
			sleep(1);
610

    
611
		/* generate hosts file */
612
		if(system_hosts_generate()!=0)
613
			$return = 1;
614

    
615
		$args = "";
616

    
617
		//if (isset($config['dnsmasq']['regdhcp'])) {
618
		//	$args .= " -l {$g['dhcpd_chroot_path']}/var/db/dhcpd.leases" .
619
		//		" -s {$config['system']['domain']}";
620
		//}
621

    
622
		if (isset($config['dnsmasq']['domainoverrides']) && is_array($config['dnsmasq']['domainoverrides'])) {
623
			foreach($config['dnsmasq']['domainoverrides'] as $override) {
624
			        $args .= ' --server=/' . $override['domain'] . '/' . $override['ip'];
625
			}
626
		}
627

    
628
		/* suppose that dnsmasq handles our domain and don't send
629
		requests for our local domain to upstream servers */
630
		//if (!empty($config['system']['domain'])) {
631
		//	$args .= sprintf(' --local=/%s/', $config['system']['domain']);
632
		//}
633

    
634
		/* run dnsmasq */
635
		mwexec("/usr/local/sbin/dnsmasq --all-servers --dns-forward-max=5000 --cache-size=10000 {$args}");
636

    
637
		if ($g['booting'])
638
			echo "done.\n";
639
	}
640

    
641
	if (!$g['booting']) {
642
		if(services_dhcpd_configure()!=0)
643
			$return = 1;
644
	}
645

    
646
	// restart isc-dhcpd parser
647
	services_parse_dhcpd_hostnames();
648

    
649
	return $return;
650
}
651

    
652
function services_snmpd_configure() {
653
	global $config, $g;
654
	if(isset($config['system']['developerspew'])) {
655
		$mt = microtime();
656
		echo "services_snmpd_configure() being called $mt\n";
657
	}
658

    
659
	/* kill any running snmpd */
660
	sigkillbypid("{$g['varrun_path']}/snmpd.pid", "TERM");
661
	if(is_process_running("bsnmpd")) 
662
		mwexec("/usr/bin/killall bsnmpd", true);
663

    
664
	if (isset($config['snmpd']['enable'])) {
665

    
666
		if ($g['booting'])
667
			echo "Starting SNMP daemon... ";
668

    
669
		/* generate snmpd.conf */
670
		$fd = fopen("{$g['varetc_path']}/snmpd.conf", "w");
671
		if (!$fd) {
672
			printf("Error: cannot open snmpd.conf in services_snmpd_configure().\n");
673
			return 1;
674
		}
675

    
676

    
677
		$snmpdconf = <<<EOD
678
location := "{$config['snmpd']['syslocation']}"
679
contact := "{$config['snmpd']['syscontact']}"
680
read := "{$config['snmpd']['rocommunity']}"
681

    
682
EOD;
683

    
684
/* No docs on what write strings do there for disable for now.
685
		if(isset($config['snmpd']['rwenable']) && preg_match('/^\S+$/', $config['snmpd']['rwcommunity'])){
686
		    $snmpdconf .= <<<EOD
687
# write string
688
write := "{$config['snmpd']['rwcommunity']}"
689

    
690
EOD;
691
		}
692
*/
693

    
694

    
695
		if(isset($config['snmpd']['trapenable']) && preg_match('/^\S+$/', $config['snmpd']['trapserver'])){
696
		    $snmpdconf .= <<<EOD
697
# SNMP Trap support.
698
traphost := {$config['snmpd']['trapserver']}
699
trapport := {$config['snmpd']['trapserverport']}
700
trap := "{$config['snmpd']['trapstring']}"
701

    
702

    
703
EOD;
704
		}
705

    
706

    
707
		$snmpdconf .= <<<EOD
708
system := 1     # pfSense
709
%snmpd
710
begemotSnmpdDebugDumpPdus       = 2
711
begemotSnmpdDebugSyslogPri      = 7
712
begemotSnmpdCommunityString.0.1 = $(read)
713

    
714
EOD;
715

    
716
/* No docs on what write strings do there for disable for now.
717
		if(isset($config['snmpd']['rwcommunity']) && preg_match('/^\S+$/', $config['snmpd']['rwcommunity'])){
718
		    $snmpdconf .= <<<EOD
719
begemotSnmpdCommunityString.0.2 = $(write)
720

    
721
EOD;
722
		}
723
*/
724

    
725

    
726
		if(isset($config['snmpd']['trapenable']) && preg_match('/^\S+$/', $config['snmpd']['trapserver'])){
727
		    $snmpdconf .= <<<EOD
728
begemotTrapSinkStatus.[$(traphost)].$(trapport) = 4
729
begemotTrapSinkVersion.[$(traphost)].$(trapport) = 2
730
begemotTrapSinkComm.[$(traphost)].$(trapport) = $(trap)
731

    
732
EOD;
733
		}
734

    
735

    
736
		$snmpdconf .= <<<EOD
737
begemotSnmpdCommunityDisable    = 1
738

    
739
EOD;
740

    
741
		if(isset($config['snmpd']['bindlan'])) {
742
			$bind_to_ip = get_interface_ip("lan");
743
		} else {
744
			$bind_to_ip = "0.0.0.0";
745
		}
746

    
747
		if(is_port( $config['snmpd']['pollport'] )) {
748
		    $snmpdconf .= <<<EOD
749
begemotSnmpdPortStatus.{$bind_to_ip}.{$config['snmpd']['pollport']} = 1
750

    
751
EOD;
752

    
753
		}
754

    
755
		$snmpdconf .= <<<EOD
756
begemotSnmpdLocalPortStatus."/var/run/snmpd.sock" = 1
757
begemotSnmpdLocalPortType."/var/run/snmpd.sock" = 4
758

    
759
# These are bsnmp macros not php vars.
760
sysContact      = $(contact)
761
sysLocation     = $(location)
762
sysObjectId     = 1.3.6.1.4.1.12325.1.1.2.1.$(system)
763

    
764
snmpEnableAuthenTraps = 2
765

    
766
EOD;
767

    
768
		if (is_array( $config['snmpd']['modules'] )) {
769
		    if(isset($config['snmpd']['modules']['mibii'])) {
770
			$snmpdconf .= <<<EOD
771
begemotSnmpdModulePath."mibII"  = "/usr/lib/snmp_mibII.so"
772

    
773
EOD;
774
		    }
775

    
776
		    if(isset($config['snmpd']['modules']['netgraph'])) {
777
			$snmpdconf .= <<<EOD
778
begemotSnmpdModulePath."netgraph" = "/usr/lib/snmp_netgraph.so"
779
%netgraph
780
begemotNgControlNodeName = "snmpd"
781

    
782
EOD;
783
		    }
784

    
785
		    if(isset($config['snmpd']['modules']['pf'])) {
786
			$snmpdconf .= <<<EOD
787
begemotSnmpdModulePath."pf"     = "/usr/lib/snmp_pf.so"
788

    
789
EOD;
790
		    }
791

    
792
		    if(isset($config['snmpd']['modules']['hostres'])) {
793
			$snmpdconf .= <<<EOD
794
begemotSnmpdModulePath."hostres"     = "/usr/lib/snmp_hostres.so"
795

    
796
EOD;
797
		    }
798
		    if(isset($config['snmpd']['modules']['bridge'])) {
799
			$snmpdconf .= <<<EOD
800
begemotSnmpdModulePath."bridge"     = "/usr/lib/snmp_bridge.so"
801
# config must end with blank line
802

    
803

    
804
EOD;
805
		    }
806
		}
807

    
808
		fwrite($fd, $snmpdconf);
809
		fclose($fd);
810

    
811
		if (isset($config['snmpd']['bindlan'])) {
812
			$bindlan = "";
813
		}
814

    
815
		/* run bsnmpd */
816
		mwexec("/usr/sbin/bsnmpd -c {$g['varetc_path']}/snmpd.conf" .
817
			"{$bindlan} -p {$g['varrun_path']}/snmpd.pid");
818

    
819
		if ($g['booting'])
820
			echo "done.\n";
821
	}
822

    
823
	return 0;
824
}
825

    
826
function services_dnsupdate_process($int = "") {
827
	global $config, $g;
828
	if(isset($config['system']['developerspew'])) {
829
		$mt = microtime();
830
		echo "services_dnsupdate_process() being called $mt\n";
831
	}
832

    
833
	/* Dynamic DNS updating active? */
834
	if (is_array($config['dnsupdates']['dnsupdate'])) {
835
		foreach ($config['dnsupdates']['dnsupdate'] as $i => $dnsupdate) {
836
			if (!isset($dyndns['enable']))
837
				continue;
838
			if (!empty($int) && $int != $dyndns['interface'])
839
				continue;
840

    
841
			/* determine interface name */
842
			$if = get_real_interface($dyndns['interface']);
843
			$wanip = get_interface_ip($dyndns['interface']);
844
			if ($wanip) {
845

    
846
				$keyname = $dnsupdate['keyname'];
847
				/* trailing dot */
848
				if (substr($keyname, -1) != ".")
849
					$keyname .= ".";
850

    
851
				$hostname = $dnsupdate['host'];
852
				/* trailing dot */
853
				if (substr($hostname, -1) != ".")
854
					$hostname .= ".";
855

    
856
				/* write private key file
857
				   this is dumb - public and private keys are the same for HMAC-MD5,
858
				   but nsupdate insists on having both */
859
				$fd = fopen("{$g['varetc_path']}/K{$i}{$keyname}+157+00000.private", "w");
860
				$privkey .= <<<EOD
861
Private-key-format: v1.2
862
Algorithm: 157 (HMAC)
863
Key: {$dnsupdate['keydata']}
864

    
865
EOD;
866
				fwrite($fd, $privkey);
867
				fclose($fd);
868

    
869
				/* write public key file */
870
				if ($dnsupdate['keytype'] == "zone") {
871
					$flags = 257;
872
					$proto = 3;
873
				} else if ($dnsupdate['keytype'] == "host") {
874
					$flags = 513;
875
					$proto = 3;
876
				} else if ($dnsupdate['keytype'] == "user") {
877
					$flags = 0;
878
					$proto = 2;
879
				}
880

    
881
				$fd = fopen("{$g['varetc_path']}/K{$keyname}+157+00000.key", "w");
882
				fwrite($fd, "{$keyname} IN KEY {$flags} {$proto} 157 {$dnsupdate['keydata']}\n");
883
				fclose($fd);
884

    
885
				/* generate update instructions */
886
				$upinst = "";
887
				if (!empty($dnsupdate['server']))
888
					$upinst .= "server {$dnsupdate['server']}\n";
889
				$upinst .= "update delete {$dnsupdate['host']} A\n";
890
				$upinst .= "update add {$dnsupdate['host']} {$dnsupdate['ttl']} A {$wanip}\n";
891
				$upinst .= "\n";	/* mind that trailing newline! */
892

    
893
				$fd = fopen("{$g['varetc_path']}/nsupdatecmds{$i}", "w");
894
				fwrite($fd, $upinst);
895
				fclose($fd);
896

    
897
				/* invoke nsupdate */
898
				$cmd = "/usr/sbin/nsupdate -k {$g['varetc_path']}/K{$i}{$keyname}+157+00000.key";
899
				if (isset($dnsupdate['usetcp']))
900
					$cmd .= " -v";
901
				$cmd .= " {$g['varetc_path']}/nsupdatecmds{$i}";
902
	
903
				mwexec_bg($cmd);
904
			}
905
		}
906
	}
907

    
908
	return 0;
909
}
910

    
911
function setup_wireless_olsr() {
912
	global $config, $g;
913
	if(!$config['installedpackages']['olsrd'] || !$config['installedpackages'])
914
		return;
915
	if(isset($config['system']['developerspew'])) {
916
		$mt = microtime();
917
		echo "setup_wireless_olsr($interface) being called $mt\n";
918
	}
919
	conf_mount_rw();
920
	foreach($config['installedpackages']['olsrd']['config'] as $olsrd) {
921
		$olsr_enable = $olsrd['enable'];
922
		if($olsr_enable <> "on")
923
			return;
924
		$fd = fopen("{$g['varetc_path']}/olsr.conf", "w");
925

    
926
		if($olsrd['announcedynamicroute'] or $olsrd['enableannounce'] == "on") {
927
			$enableannounce .= "\nHna4\n";
928
			$enableannounce .= "{\n";
929
		if($olsrd['announcedynamicroute'])
930
			$enableannounce .= "\t{$olsrd['announcedynamicroute']}\n";
931
		if($olsrd['enableannounce'] == "on")
932
			$enableannounce .= "0.0.0.0 0.0.0.0";
933
			$enableannounce .= "\n}\n";
934
		} else {
935
			$enableannounce = "";
936
		}
937

    
938
		$olsr .= <<<EODA
939
#
940
# olsr.org OLSR daemon config file
941
#
942
# Lines starting with a # are discarded
943
#
944
# This file was generated by setup_wireless_olsr() in services.inc
945
#
946

    
947
# This file is an example of a typical
948
# configuration for a mostly static
949
# network(regarding mobility) using
950
# the LQ extention
951

    
952
# Debug level(0-9)
953
# If set to 0 the daemon runs in the background
954

    
955
DebugLevel	2
956

    
957
# IP version to use (4 or 6)
958

    
959
IpVersion	4
960

    
961
# Clear the screen each time the internal state changes
962

    
963
ClearScreen     yes
964

    
965
{$enableannounce}
966

    
967
# Should olsrd keep on running even if there are
968
# no interfaces available? This is a good idea
969
# for a PCMCIA/USB hotswap environment.
970
# "yes" OR "no"
971

    
972
AllowNoInt	yes
973

    
974
# TOS(type of service) value for
975
# the IP header of control traffic.
976
# If not set it will default to 16
977

    
978
#TosValue	16
979

    
980
# The fixed willingness to use(0-7)
981
# If not set willingness will be calculated
982
# dynamically based on battery/power status
983
# if such information is available
984

    
985
#Willingness    	4
986

    
987
# Allow processes like the GUI front-end
988
# to connect to the daemon.
989

    
990
IpcConnect
991
{
992
     # Determines how many simultaneously
993
     # IPC connections that will be allowed
994
     # Setting this to 0 disables IPC
995

    
996
     MaxConnections  0
997

    
998
     # By default only 127.0.0.1 is allowed
999
     # to connect. Here allowed hosts can
1000
     # be added
1001

    
1002
     Host            127.0.0.1
1003
     #Host            10.0.0.5
1004

    
1005
     # You can also specify entire net-ranges
1006
     # that are allowed to connect. Multiple
1007
     # entries are allowed
1008

    
1009
     #Net             192.168.1.0 255.255.255.0
1010
}
1011

    
1012
# Wether to use hysteresis or not
1013
# Hysteresis adds more robustness to the
1014
# link sensing but delays neighbor registration.
1015
# Used by default. 'yes' or 'no'
1016

    
1017
UseHysteresis	no
1018

    
1019
# Hysteresis parameters
1020
# Do not alter these unless you know
1021
# what you are doing!
1022
# Set to auto by default. Allowed
1023
# values are floating point values
1024
# in the interval 0,1
1025
# THR_LOW must always be lower than
1026
# THR_HIGH.
1027

    
1028
#HystScaling	0.50
1029
#HystThrHigh	0.80
1030
#HystThrLow	0.30
1031

    
1032

    
1033
# Link quality level
1034
# 0 = do not use link quality
1035
# 1 = use link quality for MPR selection
1036
# 2 = use link quality for MPR selection and routing
1037
# Defaults to 0
1038

    
1039
LinkQualityLevel	{$olsrd['enablelqe']}
1040

    
1041
# Link quality window size
1042
# Defaults to 10
1043

    
1044
LinkQualityWinSize	10
1045

    
1046
# Polling rate in seconds(float).
1047
# Default value 0.05 sec
1048

    
1049
Pollrate	0.05
1050

    
1051

    
1052
# TC redundancy
1053
# Specifies how much neighbor info should
1054
# be sent in TC messages
1055
# Possible values are:
1056
# 0 - only send MPR selectors
1057
# 1 - send MPR selectors and MPRs
1058
# 2 - send all neighbors
1059
#
1060
# defaults to 0
1061

    
1062
TcRedundancy	2
1063

    
1064
#
1065
# MPR coverage
1066
# Specifies how many MPRs a node should
1067
# try select to reach every 2 hop neighbor
1068
#
1069
# Can be set to any integer >0
1070
#
1071
# defaults to 1
1072

    
1073
MprCoverage	3
1074

    
1075
# Example plugin entry with parameters:
1076

    
1077
EODA;
1078

    
1079
if($olsrd['enablehttpinfo'] == "on") {
1080
	$olsr .= <<<EODB
1081

    
1082
LoadPlugin "/usr/local/lib/olsrd_httpinfo.so.0.1"
1083
{
1084
    PlParam     "port"   "{$olsrd['port']}"
1085
    PlParam     "Net"    "{$olsrd['allowedhttpinfohost']} {$olsrd['allowedhttpinfosubnet']}"
1086
}
1087

    
1088
EODB;
1089

    
1090
}
1091

    
1092
if($olsrd['enabledsecure'] == "on") {
1093
	$olsr .= <<<EODC
1094

    
1095
LoadPlugin "/usr/local/lib/olsrd_secure.so.0.5"
1096
{
1097
    PlParam     "Keyfile"   "/usr/local/etc/olsrkey.txt"
1098
}
1099

    
1100
EODC;
1101

    
1102
}
1103

    
1104
if($olsrd['enabledyngw'] == "on") {
1105

    
1106
	/* unset default route, olsr auto negotiates */
1107
	mwexec("/sbin/route delete default");
1108

    
1109
	$olsr .= <<<EODE
1110

    
1111
LoadPlugin "/usr/local/lib/olsrd_dyn_gw.so.0.4"
1112
{
1113
    # how often to look for a inet gw, in seconds
1114
    # defaults to 5 secs, if commented out
1115
    PlParam     "Interval"   "{$olsrd['polling']}"
1116

    
1117
    # if one or more IPv4 addresses are given, do a ping on these in
1118
    # descending order to validate that there is not only an entry in
1119
    # routing table, but also a real internet connection. If any of
1120
    # these addresses could be pinged successfully, the test was
1121
    # succesful, i.e. if the ping on the 1st address was successful,the
1122
    # 2nd won't be pinged
1123
    PlParam     "Ping"       "{$olsrd['ping']}"
1124
    #PlParam     "HNA"   "192.168.81.0 255.255.255.0"
1125
}
1126

    
1127
EODE;
1128

    
1129
}
1130

    
1131
foreach($config['installedpackages']['olsrd']['config'] as $conf) {
1132
	$interfaces = explode(',', $conf['iface_array']);
1133
	foreach($interfaces as $interface) {
1134
		$realinterface = convert_friendly_interface_to_real_interface_name($interface);
1135
$olsr .= <<<EODAD
1136
Interface "{$realinterface}"
1137
{
1138

    
1139
    # Hello interval in seconds(float)
1140
    HelloInterval    2.0
1141

    
1142
    # HELLO validity time
1143
    HelloValidityTime	20.0
1144

    
1145
    # TC interval in seconds(float)
1146
    TcInterval        5.0
1147

    
1148
    # TC validity time
1149
    TcValidityTime	30.0
1150

    
1151
    # MID interval in seconds(float)
1152
    MidInterval	5.0
1153

    
1154
    # MID validity time
1155
    MidValidityTime	30.0
1156

    
1157
    # HNA interval in seconds(float)
1158
    HnaInterval	5.0
1159

    
1160
    # HNA validity time
1161
    HnaValidityTime 	30.0
1162

    
1163
    # When multiple links exist between hosts
1164
    # the weight of interface is used to determine
1165
    # the link to use. Normally the weight is
1166
    # automatically calculated by olsrd based
1167
    # on the characteristics of the interface,
1168
    # but here you can specify a fixed value.
1169
    # Olsrd will choose links with the lowest value.
1170

    
1171
    # Weight 0
1172

    
1173

    
1174
}
1175

    
1176
EODAD;
1177

    
1178
	}
1179
	break;
1180
}
1181
		fwrite($fd, $olsr);
1182
		fclose($fd);
1183
	}
1184

    
1185
	if(is_process_running("olsrd"))
1186
		mwexec("/usr/bin/killall olsrd", true);
1187

    
1188
	sleep(2);
1189

    
1190
	mwexec_bg("/usr/local/sbin/olsrd -f {$g['varetc_path']}/olsr.conf");
1191

    
1192
	conf_mount_ro();
1193
}
1194

    
1195
/* configure cron service */
1196
function configure_cron() {
1197
	global $g, $config;
1198
	conf_mount_rw();
1199
	/* preserve existing crontab entries */
1200
	$crontab_contents = file_get_contents("/etc/crontab");
1201
	$crontab_contents_a = split("\n", $crontab_contents);
1202
	
1203
	for ($i = 0; $i < count($crontab_contents_a); $i++) {
1204
		$item =& $crontab_contents_a[$i];
1205
		if (strpos($item, "# pfSense specific crontab entries") !== false) {
1206
			array_splice($crontab_contents_a, $i - 1);
1207
			break;
1208
		}
1209
	}
1210
	$crontab_contents = implode("\n", $crontab_contents_a) . "\n";
1211
	
1212
	
1213
	if (is_array($config['cron']['item'])) {
1214
		$crontab_contents .= "#\n";
1215
		$crontab_contents .= "# pfSense specific crontab entries\n";
1216
		$crontab_contents .= "# Created: " . date("F j, Y, g:i a") . "\n";
1217
		$crontab_contents .= "#\n";
1218

    
1219
		foreach ($config['cron']['item'] as $item) {
1220
			$crontab_contents .= "\n{$item['minute']}\t";
1221
			$crontab_contents .= "{$item['hour']}\t";
1222
			$crontab_contents .= "{$item['mday']}\t";
1223
			$crontab_contents .= "{$item['month']}\t";
1224
			$crontab_contents .= "{$item['wday']}\t";
1225
			$crontab_contents .= "{$item['who']}\t";
1226
			$crontab_contents .= "{$item['command']}";
1227
		}
1228
    
1229
		$crontab_contents .= "\n#\n";
1230
		$crontab_contents .= "# If possible do not add items to this file manually.\n";
1231
		$crontab_contents .= "# If you do so, this file must be terminated with a blank line (e.g. new line)\n";
1232
		$crontab_contents .= "#\n\n";
1233
	}
1234
	
1235
	/* please maintain the newline at the end of file */
1236
	file_put_contents("/etc/crontab", $crontab_contents);
1237
	
1238
	if (!$g['booting'])
1239
		conf_mount_ro();
1240
}
1241

    
1242
function upnp_action ($action) {
1243
	switch($action) {
1244
		case "start":
1245
			if(file_exists('/var/etc/miniupnpd.conf'))
1246
				mwexec_bg('/usr/local/sbin/miniupnpd -f /var/etc/miniupnpd.conf');
1247
			break;
1248
		case "stop":
1249
			while((int)exec("pgrep miniupnpd | wc -l") > 0)
1250
				mwexec('killall miniupnpd 2>/dev/null', true);
1251
			mwexec('/sbin/pfctl -aminiupnpd -Fr 2>&1 >/dev/null');
1252
			mwexec('/sbin/pfctl -aminiupnpd -Fn 2>&1 >/dev/null');
1253
			break;
1254
		case "restart":
1255
			upnp_action('stop');
1256
			upnp_action('start');
1257
			break;
1258
	}
1259
}
1260

    
1261
function upnp_start() {
1262
	global $config, $g;
1263
	if($config['installedpackages']['miniupnpd']['config'][0]['enable']) {
1264
		if($g['booting']) {
1265
			echo "Starting UPnP service... ";
1266
			include('/usr/local/pkg/miniupnpd.inc');
1267
			sync_package_miniupnpd();
1268
			echo "done.\n";
1269
		}
1270
		else {
1271
			upnp_action('start');
1272
		}
1273
	}
1274
}
1275

    
1276
?>
(36-36/51)