Project

General

Profile

Download (45.4 KB) Statistics
| Branch: | Tag: | Revision:
1
<?php
2
/* $Id$ */
3
/*
4
	interfaces.inc
5
	Copyright (C) 2004-2006 Scott Ullrich
6
	All rights reserved.
7

    
8
	function interfaces_wireless_configure is
9
	Copyright (C) 2005 Espen Johansen
10
	All rights reserved.
11

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

    
16
	Redistribution and use in source and binary forms, with or without
17
	modification, are permitted provided that the following conditions are met:
18

    
19
	1. Redistributions of source code must retain the above copyright notices,
20
	   this list of conditions and the following disclaimer.
21

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

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

    
38
/* include all configuration functions */
39
require_once("functions.inc");
40

    
41
function interfaces_loopback_configure() {
42
	mwexec("/sbin/ifconfig lo0 127.0.0.1");
43

    
44
	return 0;
45
}
46

    
47
function interfaces_vlan_configure() {
48
	global $config;
49

    
50
	if (is_array($config['vlans']['vlan']) && count($config['vlans']['vlan'])) {
51

    
52
		/* devices with native VLAN support */
53
		$vlan_native_supp = explode(" ", "bge em gx nge ti txp");
54

    
55
		/* devices with long frame support */
56
		$vlan_long_supp = explode(" ", "dc fxp sis ste tl tx xl");
57

    
58
		$i = 0;
59

    
60
		foreach ($config['vlans']['vlan'] as $vlan) {
61

    
62
			$cmd = "/sbin/ifconfig vlan{$i} create vlan " .
63
				escapeshellarg($vlan['tag']) . " vlandev " .
64
				escapeshellarg($vlan['if']);
65

    
66
			/* get driver name */
67
			for ($j = 0; $j < strlen($vlan['if']); $j++) {
68
				if ($vlan['if'][$j] >= '0' && $vlan['if'][$j] <= '9')
69
					break;
70
			}
71
			$drvname = substr($vlan['if'], 0, $j);
72

    
73
			if (in_array($drvname, $vlan_native_supp))
74
				$cmd .= " link0";
75
			else if (in_array($drvname, $vlan_long_supp))
76
				$cmd .= " mtu 1500";
77

    
78
			mwexec($cmd);
79

    
80
			/* invalidate interface cache */
81
			get_interface_arr(true);
82

    
83
			/* make sure the parent interface is up */
84
			mwexec("/sbin/ifconfig " . escapeshellarg($vlan['if']) . " up");
85

    
86
			$i++;
87
		}
88
	}
89

    
90
	return 0;
91
}
92

    
93
function interfaces_lan_configure() {
94
	global $config, $g;
95

    
96
	$bridges_total = get_next_available_bridge_interface();
97

    
98
	$lancfg = $config['interfaces']['lan'];
99

    
100
	/* if user has removed ip address, clear it*/
101
	if($lancfg['ipaddr'] == "")
102
		mwexec("/sbin/ifconfig {$lancfg['if']} delete");
103

    
104
	/* wireless configuration? */
105
	if (is_array($lancfg['wireless']))
106
		interfaces_wireless_configure($lancfg['if'], $lancfg['wireless']);
107

    
108
	/* MAC spoofing? */
109
	if ($lancfg['spoofmac']) {
110
		mwexec("/sbin/ifconfig " . escapeshellarg($lancfg['if']) .
111
			" link " . escapeshellarg($lancfg['spoofmac']));
112
	} else {
113
		$mac = get_interface_mac_address($lancfg['if']);
114
		if($mac == "ff:ff:ff:ff:ff:ff") {
115
			/*   this is not a valid mac address.  generate a
116
			 *   temporary mac address so the machine can get online.
117
			 */
118
			echo "Generating new MAC address.";
119
			$random_mac = generate_random_mac_address();
120
			mwexec("/sbin/ifconfig " . escapeshellarg($lancfg['if']) .
121
				" link " . escapeshellarg($random_mac));
122
			$lancfg['spoofmac'] = $random_mac;
123
			write_config();
124
			file_notice("MAC Address altered", "The INVALID MAC address (ff:ff:ff:ff:ff:ff) on interface {$lancfg['if']} has been automatically replaced with {$random_mac}", "Interfaces");
125
		}
126
	}
127

    
128
	/* bridged? */
129

    
130
	if ($lancfg['bridge']) {
131
		/* use open/netBSD style bridge */
132
		mwexec("/sbin/ifconfig bridge{$bridges_total} create");
133

    
134
		/* force all bridged interfaces to use same mtu */
135
		$mtu = get_interface_mtu($config['interfaces'][$lancfg['bridge']]['if']);
136
		mwexec("/sbin/ifconfig {$lancfg['if']} mtu {$mtu}");
137
		mwexec("/sbin/ifconfig {$config['interfaces'][$lancfg['bridge']]['if']} mtu {$mtu}");
138

    
139
		/* assign items to a bridge */
140
		mwexec("/sbin/ifconfig bridge{$bridges_total} addm {$lancfg['if']} addm {$config['interfaces'][$lancfg['bridge']]['if']}");
141

    
142
		if(!is_interface_wireless($lancfg['if']) and
143
		   !is_interface_wireless($config['interfaces'][$lancfg['bridge']]['if']))
144
			mwexec("/sbin/ifconfig bridge{$bridges_total} stp {$config['interfaces'][$lancfg['bridge']]['if']} stp {$lancfg['if']}");
145

    
146
		/* log commands run for debugging in /tmp/ */
147
		$fd = fopen("{$g['tmp_path']}/bridge_config_{$lancfg['if']}", "w");
148
		fwrite($fd, "/sbin/ifconfig {$lancfg['if']} mtu {$mtu}\n");
149
		fwrite($fd, "/sbin/ifconfig {$config['interfaces'][$lancfg['bridge']]['if']} mtu {$mtu}\n");
150
		fwrite($fd, "/sbin/ifconfig bridge{$bridges_total} create\n");
151
		fwrite($fd, "/sbin/ifconfig bridge{$bridges_total} addm {$lancfg['if']} addm {$config['interfaces'][$lancfg['bridge']]['if']}\n");
152
		fwrite($fd, "/sbin/ifconfig bridge{$bridges_total} stp {$lancfg['if']} stp {$config['interfaces'][$lancfg['bridge']]['if']}\n");
153
		fclose($fd);
154

    
155
		/* bring up interfaces */
156
		mwexec("/sbin/ifconfig bridge{$bridges_total} down");
157
		usleep(100);
158
		mwexec("/sbin/ifconfig {$config['interfaces'][$lancfg['bridge']]['if']} up");
159
		usleep(5);
160
		mwexec("/sbin/ifconfig {$lancfg['if']} up");
161
		usleep(5);
162
		mwexec("/sbin/ifconfig bridge{$bridges_total} up");
163

    
164
		$bridges_total++;
165
		/* update cache */
166
		if ($bridges_total != find_number_of_created_bridges())
167
			find_number_of_created_bridges(true);
168
	}
169

    
170
	/* media */
171
	if ($lancfg['media'] || $lancfg['mediaopt']) {
172
		$cmd = "/sbin/ifconfig " . escapeshellarg($lancfg['if']);
173
		if ($lancfg['media'])
174
			$cmd .= " media " . escapeshellarg($lancfg['media']);
175
		if ($lancfg['mediaopt'])
176
			$cmd .= " mediaopt " . escapeshellarg($lancfg['mediaopt']);
177
		mwexec($cmd);
178
	}
179

    
180
	mwexec("/sbin/ifconfig " . escapeshellarg($lancfg['if']) . " " .
181
		escapeshellarg($lancfg['ipaddr'] . "/" . $lancfg['subnet']));
182

    
183
	if (!$g['booting']) {
184
		/* make new hosts file */
185
		system_hosts_generate();
186

    
187
		/* reconfigure static routes (kernel may have deleted them) */
188
		system_routing_configure();
189

    
190
		/* set the reload filter dity flag */
191
		touch("{$g['tmp_path']}/filter_dirty");
192

    
193
		/* reload IPsec tunnels */
194
		vpn_ipsec_configure();
195

    
196
		/* reload dhcpd (gateway may have changed) */
197
		services_dhcpd_configure();
198

    
199
		/* reload dnsmasq */
200
		services_dnsmasq_configure();
201

    
202
		/* reload captive portal */
203
		captiveportal_configure();
204

    
205
	}
206

    
207
	return 0;
208
}
209

    
210
function interfaces_optional_configure() {
211
	global $config, $g;
212
	global $bridgeconfig;
213

    
214
	for ($i = 1; isset($config['interfaces']['opt' . $i]); $i++) {
215
		interfaces_optional_configure_if($i);
216
	}
217

    
218
	if (!$g['booting']) {
219
		/* reconfigure static routes (kernel may have deleted them) */
220
		system_routing_configure();
221

    
222
		/* reload IPsec tunnels */
223
		vpn_ipsec_configure();
224

    
225
		/* reload dhcpd (interface enabled/disabled/bridged status may have changed) */
226
		services_dhcpd_configure();
227

    
228
		/* restart dnsmasq */
229
		services_dnsmasq_configure();
230

    
231
		/* reload captive portal */
232
		captiveportal_configure();
233

    
234
		/* set the reload filter dity flag */
235
		touch("{$g['tmp_path']}/filter_dirty");
236
	}
237

    
238
	return 0;
239
}
240

    
241
function interfaces_optional_configure_if($opti) {
242
	global $config, $g;
243
	global $bridgeconfig, $debugging;
244

    
245
	$bridges_total = get_next_available_bridge_interface();
246

    
247
	$optcfg = $config['interfaces']['opt' . $opti];
248

    
249
	if ($g['booting']) {
250
		$optdescr = "";
251
		if ($optcfg['descr'])
252
			$optdescr = " ({$optcfg['descr']})";
253
		print "\tOPT{$opti}{$optdescr}... ";
254
	}
255

    
256
	if (isset($optcfg['enable'])) {
257
		/* wireless configuration? */
258
		if (is_array($optcfg['wireless']))
259
			interfaces_wireless_configure($optcfg['if'], $optcfg['wireless']);
260

    
261
		/* MAC spoofing? */
262
		if ($optcfg['spoofmac']) {
263
			mwexec("/sbin/ifconfig " . escapeshellarg($optcfg['if']) .
264
				" link " . escapeshellarg($optcfg['spoofmac']));
265
		} else {
266
			$mac = get_interface_mac_address($optcfg['if']);
267
			if($mac == "ff:ff:ff:ff:ff:ff") {
268
				/*   this is not a valid mac address.  generate a
269
				 *   temporary mac address so the machine can get online.
270
				 */
271
				echo "Generating new MAC address.";
272
				$random_mac = generate_random_mac_address();
273
				mwexec("/sbin/ifconfig " . escapeshellarg($optcfg['if']) .
274
					" link " . escapeshellarg($random_mac));
275
				$optcfg['spoofmac'] = $random_mac;
276
				write_config();
277
				file_notice("MAC Address altered", "The INVALID MAC address (ff:ff:ff:ff:ff:ff) on interface {$optcfg['if']} has been automatically replaced with {$random_mac}", "Interfaces");
278
			}
279
		}
280

    
281
		/* media */
282
		if ($optcfg['media'] || $optcfg['mediaopt']) {
283
			$cmd = "/sbin/ifconfig " . escapeshellarg($optcfg['if']);
284
			if ($optcfg['media'])
285
				$cmd .= " media " . escapeshellarg($optcfg['media']);
286
			if ($optcfg['mediaopt'])
287
				$cmd .= " mediaopt " . escapeshellarg($optcfg['mediaopt']);
288
			mwexec($cmd);
289
		}
290

    
291
		/* bridged? */
292
		if ($optcfg['bridge']) {
293
			mwexec("/sbin/ifconfig " . escapeshellarg($optcfg['if']) . " delete up");
294
                        /* use open/netBSD style bridge */
295
			mwexec("/sbin/ifconfig bridge{$bridges_total} create");
296

    
297
			/* invalidate interface cache */
298
			get_interface_arr(true);
299

    
300
			/* force all bridged interfaces to use same mtu */
301
			$mtu = get_interface_mtu($config['interfaces'][$optcfg['bridge']]['if']);
302
			mwexec("/sbin/ifconfig {$optcfg['if']} mtu {$mtu}");
303
			mwexec("/sbin/ifconfig {$config['interfaces'][$optcfg['bridge']]['if']} mtu {$mtu}");
304

    
305
			/* assign items to a bridge */
306
                        mwexec("/sbin/ifconfig bridge{$bridges_total} addm {$optcfg['if']} addm {$config['interfaces'][$optcfg['bridge']]['if']}");
307

    
308
			if(!is_interface_wireless($optcfg['if']) and
309
			   !is_interface_wireless($config['interfaces'][$optcfg['bridge']]['if']))
310
				mwexec("/sbin/ifconfig bridge{$bridges_total} stp {$config['interfaces'][$optcfg['bridge']]['if']} stp {$optcfg['if']}");
311

    
312
			/* log commands run for debugging in /tmp/ */
313
			$fd = fopen("{$g['tmp_path']}/bridge_config_{$optcfg['if']}", "w");
314
			fwrite($fd, "/sbin/ifconfig {$optcfg['if']} mtu {$mtu}\n");
315
			fwrite($fd, "/sbin/ifconfig {$config['interfaces'][$optcfg['bridge']]['if']} mtu {$mtu}\n");
316
			fwrite($fd, "/sbin/ifconfig bridge{$bridges_total} create\n");
317
			fwrite($fd, "/sbin/ifconfig bridge{$bridges_total} addm {$optcfg['if']} addm {$config['interfaces'][$optcfg['bridge']]['if']} up\n");
318
			fwrite($fd, "/sbin/ifconfig bridge{$bridges_total} stp {$optcfg['if']} stp {$config['interfaces'][$optcfg['bridge']]['if']}\n");
319
			fclose($fd);
320

    
321
			/* bring up interfaces */
322
			mwexec("/sbin/ifconfig bridge{$bridges_total} down");
323
			usleep(100);
324
			mwexec("/sbin/ifconfig {$config['interfaces'][$optcfg['bridge']]['if']} up");
325
			usleep(5);
326
			mwexec("/sbin/ifconfig {$optcfg['if']} up");
327
			usleep(5);
328
			mwexec("/sbin/ifconfig bridge{$bridges_total} up");
329

    
330
			$bridges_total++;
331
			/* update cache */
332
			if ($bridges_total != find_number_of_created_bridges())
333
				find_number_of_created_bridges(true);
334
		} else {
335
			/* if user has selected DHCP type then act accordingly */
336
			if($optcfg['ipaddr'] == "dhcp") {
337
				interfaces_opt_dhcp_configure("opt{$opti}");
338
			} else {
339
				mwexec("/sbin/ifconfig " . escapeshellarg($optcfg['if']) . " " .
340
				escapeshellarg($optcfg['ipaddr'] . "/" . $optcfg['subnet']));
341
			}
342
		}
343
	} else {
344
		mwexec("/sbin/ifconfig " . escapeshellarg($optcfg['if']) . " delete down");
345
	}
346
	return 0;
347
}
348

    
349
function interfaces_carp_configure() {
350
	global $g, $config, $debugging;
351
	$balanacing = "";
352
	$pfsyncinterface = "";
353
	$pfsyncenabled = "";
354
	if(isset($config['system']['developerspew'])) {
355
		$mt = microtime();
356
		echo "interfaces_carp_configure() being called $mt\n";
357
	}
358
	$carp_instances_counter = 0;
359
	$total_carp_interfaces_defined = find_number_of_created_carp_interfaces();
360
	/* destroy previous interfaces */
361
	for($x=0; $x<$total_carp_interfaces_defined; $x++)
362
		mwexec("/sbin/ifconfig carp{$x} delete");
363
	if ($g['booting']) {
364
		echo "Configuring CARP interfaces...";
365
		mute_kernel_msgs();
366
	}
367
	/* suck in configuration items */
368
	if($config['installedpackages']['carpsettings']['config']) {
369
		foreach($config['installedpackages']['carpsettings']['config'] as $carp) {
370
			$pfsyncenabled = $carp['pfsyncenabled'];
371
			$balanacing = $carp['balancing'];
372
			$pfsyncinterface = $carp['pfsyncinterface'];
373
		}
374
	} else {
375
		unset($pfsyncinterface);
376
		unset($balanacing);
377
		unset($pfsyncenabled);
378
	}
379
	if($balanacing) {
380
		mwexec("/sbin/sysctl net.inet.carp.arpbalance=1");
381
		mwexec("/sbin/sysctl net.inet.carp.preempt=0");
382
	} else {
383
		mwexec("/sbin/sysctl net.inet.carp.preempt=1");
384
	}
385
	$carp_sync_int = convert_friendly_interface_to_real_interface_name($pfsyncinterface);
386
	if($g['booting']) {
387
		/*    install rules to alllow pfsync to sync up during boot
388
		 *    carp interfaces will remain down until the bootup sequence finishes
389
		 */
390
		exec("echo pass quick proto carp all keep state > /tmp/rules.boot");
391
		exec("echo pass quick proto pfsync all >> /tmp/rules.boot");
392
		exec("echo pass out proto { tcp, udp } from any to any port 53 keep state >> /tmp/rules.boot");
393
		exec("/sbin/pfctl -f /tmp/rules.boot");
394
	}
395
	/* setup pfsync interface */
396
	if($carp_sync_int and $pfsyncenabled)
397
		mwexec("/sbin/ifconfig pfsync0 syncdev {$carp_sync_int} up");
398
	else
399
		mwexec("/sbin/ifconfig pfsync0 syncdev lo0 up");
400
	$fd = fopen("/tmp/carp.sh", "w");
401
	if($config['virtualip']['vip']) {
402
		$viparr = &$config['virtualip']['vip'];
403
		mwexec("/sbin/sysctl net.inet.carp.allow=1");
404
	} else {
405
		$viparr = array();
406
		mwexec("/sbin/sysctl net.inet.carp.allow=0");
407
	}
408
	foreach ($viparr as $vip) {
409
		if ($vip['mode'] == "carp") {
410
			$vip_password = $vip['password'];
411
			$vip_password = str_replace(" ", "", $vip_password);
412
			/* create the carp interface and setup */
413
			mwexec("/sbin/ifconfig carp" . $carp_instances_counter . " create");
414

    
415
			/* invalidate interface cache */
416
			get_interface_arr(true);
417

    
418
			$broadcast_address = gen_subnet_max($vip['subnet'], $vip['subnet_bits']);
419
			if($vip['password'] != "")
420
				$password = " pass \"" . $vip_password . "\"";
421
			if($debugging)
422
				echo "Configuring carp{$carp_instances_counter}.\n";
423
			fwrite($fd, "/sbin/ifconfig carp" . $carp_instances_counter . " " . $vip['subnet'] . "/" . $vip['subnet_bits'] . " broadcast " . $broadcast_address . " vhid " . $vip['vhid'] . "{$carpdev} advskew 200 " . $password . "\n");
424
			mwexec("/sbin/ifconfig carp" . $carp_instances_counter . " " . $vip['subnet'] . "/" . $vip['subnet_bits'] . " broadcast " . $broadcast_address . " vhid " . $vip['vhid'] . "{$carpdev} advskew 200 " . $password);
425
			mwexec("/sbin/ifconfig carp" . $carp_instances_counter . " up");
426
			fwrite($fd, "/sbin/ifconfig carp" . $carp_instances_counter . " up\n");
427
			usleep(10);
428
			$carp_instances_counter++;
429
		}
430
	}
431
	fclose($fd);
432
	mwexec("/bin/sh /tmp/carp.sh");
433
	if ($g['booting']) {
434
		unmute_kernel_msgs();
435
		echo "done.\n";
436
	}
437

    
438
	/* update cache */
439
	if ($carp_instances_counter != find_number_of_created_carp_interfaces())
440
		find_number_of_created_carp_interfaces(true);
441
}
442

    
443
function interfaces_carp_bring_up_final() {
444
	global $config, $g, $debugging;
445
	if(isset($config['system']['developerspew'])) {
446
		$mt = microtime();
447
		echo "interfaces_carp_bring_up_final() being called $mt\n";
448
	}
449
	if(!$config['installedpackages']['carpsettings']['config'])
450
		return;
451
	$viparr = &$config['virtualip']['vip'];
452
	/* could not locate an array, return */
453
	if(!is_array($viparr))
454
		return;
455
	$carp_instances_counter = 0;
456
	$counter = 0;
457
	if($g['booting'])
458
		echo "Waiting for final CARP interface bringup...";
459
	$supress = intval(`/sbin/sysctl net.inet.carp.suppress_preempt | cut -d" " -f2`);
460
	if($g['booting']) {
461
		while($supress > 0) {
462
			sleep(2);
463
			$supress = intval(`/sbin/sysctl net.inet.carp.suppress_preempt | cut -d" " -f2`);
464
			if($counter > 15)
465
				$supress = 0;
466
			$counter++;
467
			echo ".";
468
		}
469
		for($x=0; $x<23; $x++) {
470
			sleep(2);
471
			echo ".";
472
		}
473
		echo " done.\n";
474
	}
475
	foreach ($viparr as $vip) {
476
		if($debugging)
477
			echo "Upping interface carp{$carp_instances_counter}.\n";
478
		$broadcast_address = gen_subnet_max($vip['subnet'], $vip['subnet_bits']);
479
		if($vip['password'] != "")
480
			$password = " pass " . $vip['password'];
481
		if($debugging)
482
			echo "/sbin/ifconfig carp" . $carp_instances_counter . " " . $vip['subnet'] . "/" . $vip['subnet_bits'] . " broadcast " . $broadcast_address . " vhid " . $vip['vhid'] . "{$carpdev} advskew " . $vip['advskew'] . $password . "\n";
483
		mwexec("/sbin/ifconfig carp" . $carp_instances_counter . " " . $vip['subnet'] . "/" . $vip['subnet_bits'] . " broadcast " . $broadcast_address . " vhid " . $vip['vhid'] . "{$carpdev} advskew " . $vip['advskew'] . $password);
484
		sleep(1);
485
		mwexec("/sbin/ifconfig carp" . $carp_instances_counter . " up");
486
		$carp_instances_counter++;
487
	}
488
	if($g['booting'])
489
		echo " done.\n";
490
}
491

    
492
function interfaces_wireless_configure($if, $wlcfg) {
493
	global $config, $g;
494

    
495
	/*    open up a shell script that will be used to output the commands.
496
	 *    since wireless is changing a lot, these series of commands are fragile
497
     *    and will sometimes need to be verified by a operator by executing the command
498
     *    and returning the output of the command to the developers for inspection.  please
499
     *    do not change this routine from a shell script to individul exec commands.  -sullrich
500
	 */
501

    
502
	conf_mount_rw();
503

    
504
	unlink_if_exists("{$g['tmp_path']}/{$if}_setup.sh");
505

    
506
	$fd_set = fopen("/tmp/{$if}_setup.sh","w");
507
	fwrite($fd_set, "#!/bin/sh\n");
508
	fwrite($fd_set, "# pfSense wireless configuration script.\n\n");
509

    
510
	fwrite($fd_set, "# enable shell debugging\n");
511
	fwrite($fd_set, "set -x\n");
512

    
513
	/* set values for /path/program */
514
	$hostapd = "/usr/sbin/hostapd";
515
	$wpa_supplicant = "/usr/sbin/wpa_supplicant";
516
	$ifconfig = "/sbin/ifconfig";
517
	$killall = "/usr/bin/killall";
518

    
519
	/* Set all wireless ifconfig variables (splitt up to get rid of needed checking) */
520

    
521
	/* Set a/b/g standard */
522
	$standard = "mode " . escapeshellarg($wlcfg['standard']);
523

    
524
	/* Set 802.11g protection mode */
525
	$protmode = "protmode " . escapeshellarg($wlcfg['protmode']);
526

    
527
	/* set wireless channel value */
528
	if(isset($wlcfg['channel']))
529
		$channel = "channel " . escapeshellarg($wlcfg['channel']);
530

    
531
	/* set Distance value */
532
	if($wlcfg['distance'])
533
		$distance = escapeshellarg($wlcfg['distance']);
534

    
535
	/* Set ssid */
536
	if($wlcfg['ssid'])
537
		$ssid = "ssid " . escapeshellarg($wlcfg['ssid']);
538

    
539
	/* Set wireless hostap mode */
540
	if ($wlcfg['mode'] == "hostap")
541
		$hostapmode = "mediaopt hostap";
542
	else
543
		$hostapmode = "-mediaopt hostap";
544

    
545
	/* Set wireless adhoc mode */
546
	if ($wlcfg['mode'] == "adhoc")
547
		$adhocmode = "mediaopt adhoc";
548
	else
549
		$adhocmode = "-mediaopt adhoc";
550

    
551
	/* Not neccesary to set BSS mode as this is default if adhoc and/or hostap is NOT set */
552

    
553
	/* handle hide ssid option */
554
	if(isset($wlcfg['hidessid']['enable']))
555
		$hidessid = "hidessid";
556
	else
557
		$hidessid = "-hidessid";
558

    
559
	/* handle pureg (802.11g) only option */
560
	if(isset($wlcfg['pureg']['enable']))
561
		$pureg = "mode 11g pureg";
562
	else
563
		$pureg = "-pureg";
564

    
565
	/* enable apbridge option */
566
	if(isset($wlcfg['apbridge']['enable']))
567
		$apbridge = "apbridge";
568
	else
569
		$apbridge = "-apbridge";
570

    
571
	/* handle turbo option */
572
	if(isset($wlcfg['turbo']['enable']))
573
		$turbo = "mediaopt turbo";
574
	else
575
		$turbo = "-mediaopt turbo";
576

    
577
	/* handle txpower setting */
578
	if($wlcfg['txpower'] <> "")
579
		$txpower = "txpower " . escapeshellarg($wlcfg['txpower']);
580

    
581
	/* handle wme option */
582
	if(isset($wlcfg['wme']['enable']))
583
		$wme = "wme";
584
	else
585
		$wme = "-wme";
586

    
587
	/* set up wep if enabled */
588
    if (isset($wlcfg['wep']['enable']) && is_array($wlcfg['wep']['key'])) {
589
		if($wlcfg['wpa']['auth_algs'] == "1")
590
			$wepset .= "authmode open wepmode on ";
591
		else if($wlcfg['wpa']['auth_algs'] == "2")
592
			$wepset .= "authmode shared wepmode on ";
593
		else if($wlcfg['wpa']['auth_algs'] == "3")
594
			$wepset .= "authmode mixed wepmode on ";
595
		$i = 1;
596
		foreach ($wlcfg['wep']['key'] as $wepkey) {
597
			$wepset .= "wepkey " . escapeshellarg("{$i}:{$wepkey['value']}") . " ";
598
			if (isset($wepkey['txkey']))
599
				$wepset .= "weptxkey {$i} ";
600
			$i++;
601
		}
602
    } else {
603
    	$wepset .= "authmode open wepmode off ";
604
	}
605

    
606
	/* generate wpa_supplicant/hostap config if wpa is enabled */
607

    
608
	switch ($wlcfg['mode']) {
609
		case 'bss':
610
			if (isset($wlcfg['wpa']['enable'])) {
611

    
612
				$wpa .= <<<EOD
613
ctrl_interface={$g['varrun_path']}/wpa_supplicant
614
ctrl_interface_group=0
615
ap_scan=1
616
#fast_reauth=1
617
network={
618
ssid="{$wlcfg['ssid']}"
619
scan_ssid=1
620
priority=5
621
key_mgmt={$wlcfg['wpa']['wpa_key_mgmt']}
622
psk="{$wlcfg['wpa']['passphrase']}"
623
pairwise={$wlcfg['wpa']['wpa_pairwise']}
624
group={$wlcfg['wpa']['wpa_pairwise']}
625
}
626
EOD;
627

    
628
				$fd = fopen("{$g['varetc_path']}/wpa_supplicant_{$if}.conf", "w");
629
				fwrite($fd, "{$wpa}");
630
				fclose($fd);
631

    
632
				fwrite($fd_set, kill_wpasupplicant($if));
633
			}
634
		break;
635

    
636
		case 'hostap':
637
			if (isset($wlcfg['wpa']['enable'])) {
638
				$wpa .= <<<EOD
639
interface={$if}
640
driver=bsd
641
logger_syslog=-1
642
logger_syslog_level=0
643
logger_stdout=-1
644
logger_stdout_level=0
645
dump_file={$g['tmp_path']}/hostapd_{$if}.dump
646
ctrl_interface={$g['varrun_path']}/hostapd
647
ctrl_interface_group=wheel
648
#accept_mac_file={$g['tmp_path']}/hostapd_{$if}.accept
649
#deny_mac_file={$g['tmp_path']}/hostapd_{$if}.deny
650
#macaddr_acl={$wlcfg['wpa']['macaddr_acl']}
651
ssid={$wlcfg['ssid']}
652
debug={$wlcfg['wpa']['debug_mode']}
653
auth_algs={$wlcfg['wpa']['auth_algs']}
654
wpa={$wlcfg['wpa']['wpa_mode']}
655
wpa_key_mgmt={$wlcfg['wpa']['wpa_key_mgmt']}
656
wpa_pairwise={$wlcfg['wpa']['wpa_pairwise']}
657
wpa_group_rekey={$wlcfg['wpa']['wpa_group_rekey']}
658
wpa_gmk_rekey={$wlcfg['wpa']['wpa_gmk_rekey']}
659
wpa_strict_rekey={$wlcfg['wpa']['wpa_strict_rekey']}
660
wpa_passphrase={$wlcfg['wpa']['passphrase']}
661
ieee8021x={$wlcfg['wpa']['ieee8021x']}
662
#Enable the next lines for preauth when roaming. Interface = wired or wireless interface talking to the AP you want to roam from/to
663
#rsn_preauth=1
664
#rsn_preauth_interfaces=eth0
665
EOD;
666

    
667
				$fd = fopen("{$g['varetc_path']}/hostapd_{$if}.conf", "w");
668
				fwrite($fd, "{$wpa}");
669
				fclose($fd);
670

    
671
				fwrite($fd_set, kill_hostapd($if));
672
			}
673
		break;
674

    
675
		case 'adhoc':
676
			fwrite($fd_set, kill_hostapd($if));
677
			fwrite($fd_set, kill_wpasupplicant($if));
678
		break;
679
	}
680

    
681
	/*
682
	 *    all variables are set, lets start up everything
683
     */
684

    
685
	/* set ack timers according to users preference (if he/she has any) */
686
	if($distance) {
687
		fwrite($fd_set, "# Enable ATH distance settings\n");
688
		fwrite($fd_set, "/sbin/athctrl.sh -i {$if} -d {$distance}\n");
689
	}
690

    
691
	$standard_no_turbo = str_replace(" Turbo", "", $standard);
692

    
693
	$settings = <<<EOD
694

    
695
{$ifconfig} {$if} down
696
{$ifconfig} {$if} {$hostapmode}
697
{$ifconfig} {$if} {$standard_no_turbo}
698
{$ifconfig} {$if} {$channel}
699
{$ifconfig} {$if} {$turbo}
700
{$ifconfig} {$if} {$ssid}
701
{$ifconfig} {$if} {$hidessid}
702
{$ifconfig} {$if} {$adhocmode}
703
{$ifconfig} {$if} {$protmode}
704
{$ifconfig} {$if} {$pureg}
705
{$ifconfig} {$if} {$apbridge}
706
{$ifconfig} {$if} {$wme}
707
{$ifconfig} {$if} {$wepset}
708
{$ifconfig} {$if} {$txpower}
709
{$ifconfig} {$if} up
710

    
711
EOD;
712

    
713
	/* write out above <<EOD stuff */
714
	fwrite($fd_set, $settings);
715

    
716
	if (isset($wlcfg['wpa']['enable'])) {
717
		if ($wlcfg['mode'] == "bss")
718
			fwrite($fd_set, "{$wpa_supplicant} -B -i {$if} -c {$g['varetc_path']}/wpa_supplicant_{$if}.conf\n");
719
		if ($wlcfg['mode'] == "hostap")
720
			fwrite($fd_set, "{$hostapd} -B {$g['varetc_path']}/hostapd_{$if}.conf\n");
721
	}
722

    
723
	fclose($fd_set);
724

    
725
	conf_mount_ro();
726

    
727
	/* execute commands now in shell */
728
	mwexec("/bin/sh /tmp/{$if}_setup.sh");
729
	sleep(2);
730
	mwexec("/bin/sh /tmp/{$if}_setup.sh");
731

    
732
	return 0;
733

    
734
}
735

    
736
function kill_hostapd($interface) {
737
	return "/bin/ps awwuxx | grep hostapd | grep $interface | awk '{ print \$2 }' | xargs kill\n";
738
}
739

    
740
function kill_wpasupplicant($interface) {
741
	return "/bin/ps awwuxx | grep wpa_supplicant | grep $interface | awk '{ print \$2 }' | xargs kill\n";
742
}
743

    
744
function find_dhclient_process($interface) {
745
	if(filter_translate_type_to_real_interface($interface) <> "")
746
        	$realinterface = filter_translate_type_to_real_interface($interface);
747
	$pid = `/usr/bin/pgrep -f "dhclient: {$realinterface}(\$| .*)"`;
748
	return $pid;
749
}
750

    
751
function interfaces_wan_configure() {
752
	global $config, $g, $bridges_total;
753

    
754
	$wancfg = $config['interfaces']['wan'];
755

    
756
	if(!$g['booting']) {
757
		mute_kernel_msgs();
758

    
759
		/* find dhclient process for wan and kill it */
760
		killbypid(find_dhclient_process("wan"));
761

    
762
		/* remove wanup file if it exists */
763
		unlink_if_exists("{$g['tmp_path']}/wanup");
764

    
765
		/* kill PPPoE client (mpd) */
766
		killbypid("{$g['varrun_path']}/mpd.pid");
767

    
768
		/* wait for processes to die */
769
		sleep(3);
770

    
771
		unlink_if_exists("{$g['varetc_path']}/dhclient_wan.conf");
772
		unlink_if_exists("{$g['varetc_path']}/mpd.conf");
773
		unlink_if_exists("{$g['varetc_path']}/mpd.links");
774
		unlink_if_exists("{$g['vardb_path']}/wanip");
775
		unlink_if_exists("{$g['varetc_path']}/nameservers.conf");
776
	}
777

    
778
	/* remove all addresses first */
779
	while (mwexec("/sbin/ifconfig " . escapeshellarg($wancfg['if']) . " -alias") == 0);
780
	mwexec("/sbin/ifconfig " . escapeshellarg($wancfg['if']) . " down");
781

    
782
	/* wireless configuration? */
783
	if (is_array($wancfg['wireless']))
784
		interfaces_wireless_configure($wancfg['if'], $wancfg['wireless']);
785

    
786
	if ($wancfg['spoofmac']) {
787
		mwexec("/sbin/ifconfig " . escapeshellarg($wancfg['if']) .
788
			" link " . escapeshellarg($wancfg['spoofmac']));
789
	}  else {
790
		$mac = get_interface_mac_address($wancfg['if']);
791
		if($mac == "ff:ff:ff:ff:ff:ff") {
792
			/*   this is not a valid mac address.  generate a
793
			 *   temporary mac address so the machine can get online.
794
			 */
795
			echo "Generating new MAC address.";
796
			$random_mac = generate_random_mac_address();
797
			mwexec("/sbin/ifconfig " . escapeshellarg($wancfg['if']) .
798
				" link " . escapeshellarg($random_mac));
799
			$wancfg['spoofmac'] = $random_mac;
800
			write_config();
801
			file_notice("MAC Address altered", "The INVALID MAC address (ff:ff:ff:ff:ff:ff) on interface {$wancfg['if']} has been automatically replaced with {$random_mac}", "Interfaces");
802
		}
803
	}
804

    
805
	/* media */
806
	if ($wancfg['media'] || $wancfg['mediaopt']) {
807
		$cmd = "/sbin/ifconfig " . escapeshellarg($wancfg['if']);
808
		if ($wancfg['media'])
809
			$cmd .= " media " . escapeshellarg($wancfg['media']);
810
		if ($wancfg['mediaopt'])
811
			$cmd .= " mediaopt " . escapeshellarg($wancfg['mediaopt']);
812
		mwexec($cmd);
813
	}
814

    
815
	switch ($wancfg['ipaddr']) {
816

    
817
		case 'dhcp':
818
			interfaces_wan_dhcp_configure();
819
			break;
820

    
821
		case 'pppoe':
822
			interfaces_wan_pppoe_configure();
823
			break;
824

    
825
		case 'pptp':
826
			interfaces_wan_pptp_configure();
827
			break;
828

    
829
		case 'bigpond':
830
			/* just configure DHCP for now; fire up bpalogin when we've got the lease */
831
			interfaces_wan_dhcp_configure();
832
			break;
833

    
834
		default:
835
			if (isset($wancfg['ispointtopoint']) && $wancfg['pointtopoint']) {
836
				mwexec("/sbin/ifconfig " . escapeshellarg($wancfg['if']) . " " .
837
					escapeshellarg($wancfg['ipaddr'] . "/" . $wancfg['subnet']) .
838
					" " . escapeshellarg($wancfg['pointtopoint']) . " up");
839
			} else {
840
				mwexec("/sbin/ifconfig " . escapeshellarg($wancfg['if']) . " " .
841
					escapeshellarg($wancfg['ipaddr'] . "/" . $wancfg['subnet']));
842
			}
843
			/* install default route */
844
			mwexec("/sbin/route delete default");
845

    
846
			$dont_add_route = false;
847
			/* if OLSRD is enabled, allow WAN to house DHCP. */
848
			if($config['installedpackages']['olsrd']) {
849
				foreach($config['installedpackages']['olsrd']['config'] as $olsrd) {
850
						if($olsrd['enabledyngw'] == "on") {
851
							$dont_add_route = true;
852
						}
853
				}
854
			}
855

    
856
			if($dont_add_route == false)
857
				mwexec("/sbin/route add default " . escapeshellarg($config['interfaces']['wan']['gateway']));
858

    
859
			/* resync pf (done automatically for DHCP/PPPoE/PPTP) */
860
			filter_configure();
861
	}
862

    
863
	if ($wancfg['bridge']) {
864
		/* use open/netBSD style bridge */
865
		mwexec("/sbin/ifconfig bridge{$bridges_total} create");
866

    
867
		/* invalidate interface cache */
868
		get_interface_arr(true);
869

    
870
		/* force all bridged interfaces to use same mtu */
871
		$mtu = get_interface_mtu($config['interfaces'][$wancfg['bridge']]['if']);
872
		mwexec("/sbin/ifconfig {$wancfg['if']} mtu {$mtu}");
873
		mwexec("/sbin/ifconfig {$config['interfaces'][$wancfg['bridge']]['if']} mtu {$mtu}");
874

    
875
		/* assign items to a bridge */
876
		mwexec("/sbin/ifconfig bridge{$bridges_total} addm {$wancfg['if']} addm {$config['interfaces'][$wancfg['bridge']]['if']}");
877

    
878
		if(!is_interface_wireless($wancfg['if']) and
879
		   !is_interface_wireless($config['interfaces'][$wancfg['bridge']]['if']))
880
			mwexec("/sbin/ifconfig bridge{$bridges_total} stp {$config['interfaces'][$wancfg['bridge']]['if']} stp {$wancfg['if']}");
881

    
882
		/* log commands run for debugging in /tmp/ */
883
		$fd = fopen("{$g['tmp_path']}/bridge_config_{$wancfg['if']}", "w");
884
		fwrite($fd, "/sbin/ifconfig {$wancfg['if']} mtu {$mtu}\n");
885
		fwrite($fd, "/sbin/ifconfig {$config['interfaces'][$wancfg['bridge']]['if']} mtu {$mtu}\n");
886
		fwrite($fd, "/sbin/ifconfig bridge{$bridges_total} create\n");
887
		fwrite($fd, "/sbin/ifconfig bridge{$bridges_total} addm {$wancfg['if']} addm {$config['interfaces'][$wancfg['bridge']]['if']}\n");
888
		fwrite($fd, "/sbin/ifconfig bridge{$bridges_total} stp {$wancfg['if']} stp {$config['interfaces'][$wancfg['bridge']]['if']}\n");
889
		fclose($fd);
890

    
891
		/* bring up interfaces */
892
		mwexec("/sbin/ifconfig bridge{$bridges_total} down");
893
		usleep(100);
894
		mwexec("/sbin/ifconfig {$config['interfaces'][$wancfg['bridge']]['if']} up");
895
		usleep(5);
896
		mwexec("/sbin/ifconfig {$wancfg['if']} up");
897
		usleep(5);
898
		mwexec("/sbin/ifconfig bridge{$bridges_total} up");
899

    
900
		$bridges_total++;
901
		/* update cache */
902
		if ($bridges_total != find_number_of_created_bridges())
903
			find_number_of_created_bridges(true);
904
	}
905

    
906
	if (!$g['booting']) {
907
		/* reconfigure static routes (kernel may have deleted them) */
908
		system_routing_configure();
909

    
910
		/* set the reload filter dity flag */
911
		touch("{$g['tmp_path']}/filter_dirty");
912

    
913
		/* reload ipsec tunnels */
914
		vpn_ipsec_configure();
915

    
916
		/* restart ez-ipupdate */
917
		services_dyndns_configure();
918

    
919
		/* force DNS update */
920
		services_dnsupdate_process();
921

    
922
		/* restart dnsmasq */
923
		services_dnsmasq_configure();
924

    
925
		/* reload captive portal */
926
		captiveportal_configure();
927
	}
928

    
929
	mwexec("/sbin/ifconfig {$wancfg['if']} up");
930

    
931
	unmute_kernel_msgs();
932

    
933
	return 0;
934
}
935

    
936
function interfaces_opt_dhcp_configure($interface) {
937
	global $config, $g;
938

    
939
	$optcfg = $config['interfaces'][$interface];
940
	$optif = $optcfg['if'];
941

    
942
	/* generate dhclient_wan.conf */
943
	$fd = fopen("{$g['varetc_path']}/dhclient_{$optif}.conf", "w");
944
	if (!$fd) {
945
		printf("Error: cannot open dhclient_{$optif}.conf in interfaces_opt_dhcp_configure({$optif}) for writing.\n");
946
		return 1;
947
	}
948

    
949
	if ($optcfg['dhcphostname']) {
950
		$dhclientconf_hostname = "send dhcp-client-identifier \"{$optcfg['dhcphostname']}\";\n";
951
		$dhclientconf_hostname .= "send host-name \"{$optcfg['dhcphostname']}\";\n";
952
	} else {
953
		$dhclientconf_hostname = "";
954
	}
955

    
956
 	$dhclientconf = "";
957

    
958
	$dhclientconf .= <<<EOD
959
interface "{$optif}" {
960
	script "/sbin/dhclient-script";
961
	{$dhclientconf_hostname}
962
}
963

    
964
EOD;
965

    
966
	fwrite($fd, $dhclientconf);
967
	fclose($fd);
968

    
969
        /* bring interface up before starting dhclient */
970
        mwexec("/sbin/ifconfig {$optif} up");
971

    
972
        /* fire up dhclient */
973
        mwexec("/sbin/dhclient -c {$g['varetc_path']}/dhclient_{$optif}.conf {$optif}");
974

    
975
	return 0;
976
}
977

    
978
function interfaces_dhcp_configure($interface) {
979
	global $config, $g;
980

    
981
	if(filter_translate_type_to_real_interface($interface) <> "")
982
        	$realinterface = filter_translate_type_to_real_interface($interface);
983

    
984
	$optcfg = $config['interfaces'][$interface];
985

    
986
	/* generate dhclient_$interface.conf */
987
	$fd = fopen("{$g['varetc_path']}/dhclient_{$interface}.conf", "w");
988
	if (!$fd) {
989
		printf("Error: cannot open dhclient_{$interface}.conf in interfaces_dhcp_configure({$$interface}) for writing.\n");
990
		return 1;
991
	}
992

    
993
	if ($optcfg['dhcphostname']) {
994
		$dhclientconf_hostname =  "send dhcp-client-identifier \"{$optcfg['dhcphostname']}\";\n";
995
		$dhclientconf_hostname .= "send host-name \"{$optcfg['dhcphostname']}\";\n";
996
	} else {
997
		$dhclientconf_hostname = "";
998
	}
999

    
1000
 	$dhclientconf = "";
1001

    
1002
	$dhclientconf .= <<<EOD
1003
interface "{$realinterface}" {
1004
	{$dhclientconf_hostname}
1005
	script "/sbin/dhclient-script";
1006
}
1007

    
1008
EOD;
1009

    
1010
	fwrite($fd, $dhclientconf);
1011
	fclose($fd);
1012

    
1013
	$optif = $optcfg['if'];
1014

    
1015
        /* bring wan interface up before starting dhclient */
1016
        mwexec("/sbin/ifconfig {$optif} up");
1017

    
1018
        /* fire up dhclient */
1019
        mwexec("/sbin/dhclient -c {$g['varetc_path']}/dhclient_{$optif}.conf {$optif} >/tmp/{$optif}_output >/tmp/{$optif}_error_output");
1020

    
1021
	$fout = fopen("/tmp/ifconfig_{$optif}","w");
1022
	fwrite($fout, "/sbin/dhclient -c {$g['varetc_path']}/dhclient_{$optif}.conf {$optif}");
1023
	fclose($fout);
1024

    
1025
	return 0;
1026
}
1027

    
1028
function interfaces_wan_dhcp_configure() {
1029
	global $config, $g;
1030

    
1031
	$wancfg = $config['interfaces']['wan'];
1032

    
1033
	/* generate dhclient_wan.conf */
1034
	$fd = fopen("{$g['varetc_path']}/dhclient_wan.conf", "w");
1035
	if (!$fd) {
1036
		printf("Error: cannot open dhclient_wan.conf in interfaces_wan_dhcp_configure() for writing.\n");
1037
		return 1;
1038
	}
1039

    
1040
	if ($wancfg['dhcphostname']) {
1041
		$dhclientconf_hostname = "send dhcp-client-identifier \"{$wancfg['dhcphostname']}\";\n";
1042
		$dhclientconf_hostname .= "send host-name \"{$optcfg['dhcphostname']}\";\n";
1043
	} else {
1044
		$dhclientconf_hostname = "";
1045
	}
1046

    
1047
 	$dhclientconf = "";
1048

    
1049
	$dhclientconf .= <<<EOD
1050
interface "{$wancfg['if']}" {
1051
	{$dhclientconf_hostname}
1052
	script "/sbin/dhclient-script";
1053
}
1054

    
1055
EOD;
1056

    
1057
	fwrite($fd, $dhclientconf);
1058
	fclose($fd);
1059

    
1060
	$wanif = $wancfg['if'];
1061

    
1062
        /* bring wan interface up before starting dhclient */
1063
        mwexec("/sbin/ifconfig {$wanif} up");
1064

    
1065
        /* fire up dhclient */
1066
        mwexec("/sbin/dhclient -c {$g['varetc_path']}/dhclient_wan.conf {$wanif} >/tmp/{$wanif}_output >/tmp/{$wanif}_error_output");
1067

    
1068
	$fout = fopen("/tmp/ifconfig_{$wanif}","w");
1069
	fwrite($fout, "/sbin/dhclient -c {$g['varetc_path']}/dhclient_wan.conf {$wanif}");
1070
	fclose($fout);
1071

    
1072
	return 0;
1073
}
1074

    
1075
function interfaces_wan_dhcp_down() {
1076
	global $config;
1077
	$wancfg = $config['interfaces']['wan'];
1078
	$wanif = $wancfg['if'];
1079
	mwexec("/sbin/ifconfig {$wanif} delete");
1080
	sleep(1);
1081
}
1082

    
1083
function interfaces_dhcp_down($interface) {
1084
	global $config;
1085
	if(filter_translate_type_to_real_interface($interface) <> "")
1086
		$realinterface = filter_translate_type_to_real_interface($interface);
1087
	mwexec("/sbin/ifconfig {$realinterface} down");
1088
	sleep(1);
1089
	$pid = find_dhclient_process($interface);
1090
	if($pid)
1091
		mwexec("kill {$pid}");
1092
}
1093

    
1094
function interfaces_dhcp_up($interface) {
1095
	interfaces_dhcp_configure($interface);
1096
	sleep(1);
1097
}
1098

    
1099
function interfaces_wan_dhcp_up() {
1100
	interfaces_wan_dhcp_configure();
1101
	sleep(1);
1102
}
1103

    
1104
function interfaces_wan_pppoe_configure() {
1105
	global $config, $g;
1106

    
1107
	$wancfg = $config['interfaces']['wan'];
1108
	$pppoecfg = $config['pppoe'];
1109

    
1110
	/* generate mpd.conf */
1111
	$fd = fopen("{$g['varetc_path']}/mpd.conf", "w");
1112
	if (!$fd) {
1113
		printf("Error: cannot open mpd.conf in interfaces_wan_pppoe_configure().\n");
1114
		return 1;
1115
	}
1116

    
1117
	$idle = 0;
1118

    
1119
	if (isset($pppoecfg['ondemand'])) {
1120
		$ondemand = "enable";
1121
		if ($pppoecfg['timeout'])
1122
			$idle = $pppoecfg['timeout'];
1123
	} else {
1124
		$ondemand = "disable";
1125
	}
1126

    
1127
	$mpdconf = <<<EOD
1128
pppoe:
1129
	new -i ng0 pppoe pppoe
1130
	set iface route default
1131
	set iface {$ondemand} on-demand
1132
	set iface idle {$idle}
1133
	set iface up-script /usr/local/sbin/ppp-linkup
1134

    
1135
EOD;
1136

    
1137
	/*    Check for ppp-linkdown Script in /usr/local/sbin
1138
	 *    Create reference in mpd.conf
1139
	 */
1140
	if ( file_exists("/usr/local/sbin/ppp-linkdown") ){
1141
		$mpdconf .= <<<EOD
1142
	set iface down-script /usr/local/sbin/ppp-linkdown
1143

    
1144
EOD;
1145
	}
1146

    
1147
	if (isset($pppoecfg['ondemand'])) {
1148
		if (isset($pppoecfg['local-ip']) && isset($pppoecfg['remote-ip'])) {
1149
			$mpdconf .= <<<EOD
1150
	set iface addrs {$pppoecfg['local-ip']} {$pppoecfg['remote-ip']}
1151

    
1152
EOD;
1153
		} else {
1154
			$mpdconf .= <<<EOD
1155
	set iface addrs 192.0.2.112 192.0.2.113
1156

    
1157
EOD;
1158
		}
1159
	}
1160

    
1161
	$mpdconf .= <<<EOD
1162
	set bundle disable multilink
1163
	set bundle authname "{$pppoecfg['username']}"
1164
	set bundle password "{$pppoecfg['password']}"
1165
	set link keep-alive 10 60
1166
	set link max-redial 0
1167
	set link no acfcomp protocomp
1168
	set link disable pap chap
1169
	set link accept chap
1170
	set link mtu 1492
1171
	set ipcp yes vjcomp
1172
	set ipcp ranges 0.0.0.0/0 0.0.0.0/0
1173

    
1174
EOD;
1175

    
1176
	if (isset($config['system']['dnsallowoverride'])) {
1177
		$mpdconf .= <<<EOD
1178
	set ipcp enable req-pri-dns
1179

    
1180
EOD;
1181
	}
1182

    
1183
	$mpdconf .= <<<EOD
1184
	open iface
1185

    
1186
EOD;
1187

    
1188
	fwrite($fd, $mpdconf);
1189
	fclose($fd);
1190

    
1191
	/* generate mpd.links */
1192
	$fd = fopen("{$g['varetc_path']}/mpd.links", "w");
1193
	if (!$fd) {
1194
		printf("Error: cannot open mpd.links in interfaces_wan_pppoe_configure().\n");
1195
		return 1;
1196
	}
1197

    
1198
	$mpdconf = <<<EOD
1199
pppoe:
1200
	set link type pppoe
1201
	set pppoe iface {$wancfg['if']}
1202
	set pppoe service "{$pppoecfg['provider']}"
1203
	set pppoe enable originate
1204
	set pppoe disable incoming
1205

    
1206
EOD;
1207

    
1208
	fwrite($fd, $mpdconf);
1209
	fclose($fd);
1210

    
1211
	if(file_exists("{$g['varrun_path']}/mpd.pid") and $g['booting']) {
1212
		/* if we are booting and mpd has already been started then don't start again. */
1213
	} else {
1214
		/* if mpd is active, lets take it down */
1215
		if(file_exists("{$g['varrun_path']}/mpd.pid")) {
1216
			killbypid("{$g['varrun_path']}/mpd.pid");
1217
			sleep(3);
1218
		}
1219
		/* fire up mpd */
1220
		mwexec("/usr/local/sbin/mpd -b -d {$g['varetc_path']} -p {$g['varrun_path']}/mpd.pid pppoe");
1221
	}
1222

    
1223
        /* sleep until wan is up - or 30 seconds, whichever comes first */
1224
	for ($count = 0; $count < 30; $count++) {
1225
		if(file_exists("{$g['tmp_path']}/wanup")) {
1226
			break;
1227
		}
1228
		sleep(1);
1229
	}
1230

    
1231
	unlink_if_exists("{$g['tmp_path']}/wanup");
1232

    
1233
	return 0;
1234
}
1235

    
1236
function interfaces_wan_pppoe_down() {
1237
	global $g;
1238
	sigkillbypid("{$g['varrun_path']}/mpd.pid", "SIGUSR2");
1239
	sleep(1);
1240
}
1241

    
1242
function interfaces_wan_pppoe_up() {
1243
	global $g;
1244
	sigkillbypid("{$g['varrun_path']}/mpd.pid", "SIGUSR1");
1245
	sleep(1);
1246
}
1247

    
1248
function interfaces_wan_pptp_configure() {
1249
	global $config, $g;
1250

    
1251
	$wancfg = $config['interfaces']['wan'];
1252
	$pptpcfg = $config['pptp'];
1253

    
1254
	/* generate mpd.conf */
1255
	$fd = fopen("{$g['varetc_path']}/mpd.conf", "w");
1256
	if (!$fd) {
1257
		printf("Error: cannot open mpd.conf in interfaces_wan_pptp_configure().\n");
1258
		return 1;
1259
	}
1260

    
1261
	$idle = 0;
1262

    
1263
	if (isset($pptpcfg['ondemand'])) {
1264
		$ondemand = "enable";
1265
		if ($pptpcfg['timeout'])
1266
			$idle = $pptpcfg['timeout'];
1267
	} else {
1268
		$ondemand = "disable";
1269
	}
1270

    
1271
	$mpdconf = <<<EOD
1272
pptp:
1273
	new -i ng0 pptp pptp
1274
	set iface route default
1275
	set iface {$ondemand} on-demand
1276
	set iface idle {$idle}
1277
	set iface up-script /usr/local/sbin/ppp-linkup
1278

    
1279
EOD;
1280

    
1281
	/*   Check for ppp-linkdown Script in /usr/local/sbin
1282
	 *   Create reference in mpd.conf
1283
	 */
1284
	if ( file_exists("/usr/local/sbin/ppp-linkdown") ){
1285
		$mpdconf .= <<<EOD
1286
	set iface down-script /usr/local/sbin/ppp-linkdown
1287

    
1288
EOD;
1289
	}
1290

    
1291
	if (isset($pptpcfg['ondemand'])) {
1292
		$mpdconf .= <<<EOD
1293
	set iface addrs 10.0.0.1 10.0.0.2
1294

    
1295
EOD;
1296
	}
1297

    
1298
	$mpdconf .= <<<EOD
1299
	set bundle disable multilink
1300
	set bundle authname "{$pptpcfg['username']}"
1301
	set bundle password "{$pptpcfg['password']}"
1302
	set link keep-alive 10 60
1303
	set link max-redial 0
1304
	set link no acfcomp protocomp
1305
	set link disable pap chap
1306
	set link accept chap
1307
	set ipcp no vjcomp
1308
	set ipcp ranges 0.0.0.0/0 0.0.0.0/0
1309

    
1310
EOD;
1311
	if (isset($config['system']['dnsallowoverride'])) {
1312
		$mpdconf .= <<<EOD
1313
	set ipcp enable req-pri-dns
1314

    
1315
EOD;
1316
	}
1317

    
1318
	$mpdconf .= <<<EOD
1319
	open
1320

    
1321
EOD;
1322

    
1323
	fwrite($fd, $mpdconf);
1324
	fclose($fd);
1325

    
1326
	/* generate mpd.links */
1327
	$fd = fopen("{$g['varetc_path']}/mpd.links", "w");
1328
	if (!$fd) {
1329
		printf("Error: cannot open mpd.links in interfaces_wan_pptp_configure().\n");
1330
		return 1;
1331
	}
1332

    
1333
	$mpdconf = <<<EOD
1334
pptp:
1335
	set link type pptp
1336
	set pptp enable originate outcall
1337
	set pptp disable windowing
1338
	set pptp self {$pptpcfg['local']}
1339
	set pptp peer {$pptpcfg['remote']}
1340

    
1341
EOD;
1342

    
1343
	fwrite($fd, $mpdconf);
1344
	fclose($fd);
1345

    
1346
	/* configure interface */
1347
	mwexec("/sbin/ifconfig " . escapeshellarg($wancfg['if']) . " " .
1348
		escapeshellarg($pptpcfg['local'] . "/" . $pptpcfg['subnet']));
1349

    
1350
	/* fire up mpd */
1351
	mwexec("/usr/local/sbin/mpd -b -d {$g['varetc_path']} -p {$g['varrun_path']}/mpd.pid pptp");
1352

    
1353
	return 0;
1354
}
1355

    
1356
function interfaces_wan_pptp_down() {
1357
	global $g;
1358
	sigkillbypid("{$g['varrun_path']}/mpd.pid", "SIGUSR2");
1359
	sleep(1);
1360
}
1361

    
1362
function interfaces_wan_pptp_up() {
1363
	global $g;
1364
	sigkillbypid("{$g['varrun_path']}/mpd.pid", "SIGUSR1");
1365
	sleep(1);
1366
}
1367

    
1368
function interfaces_wan_bigpond_configure($curwanip) {
1369
	global $config, $g;
1370

    
1371
	$bpcfg = $config['bigpond'];
1372

    
1373
	if (!$curwanip) {
1374
		/* IP address not configured yet, exit */
1375
		return 0;
1376
	}
1377

    
1378
	/* kill bpalogin */
1379
	killbyname("bpalogin");
1380

    
1381
	/* wait a moment */
1382
	sleep(1);
1383

    
1384
	/* get the default domain */
1385
	$nfd = @fopen("{$g['varetc_path']}/defaultdomain.conf", "r");
1386
	if ($nfd) {
1387
		$defaultdomain = trim(fgets($nfd));
1388
		fclose($nfd);
1389
	}
1390

    
1391
	/* generate bpalogin.conf */
1392
	$fd = fopen("{$g['varetc_path']}/bpalogin.conf", "w");
1393
	if (!$fd) {
1394
		printf("Error: cannot open bpalogin.conf in interfaces_wan_bigpond_configure().\n");
1395
		return 1;
1396
	}
1397

    
1398
	if (!$bpcfg['authserver'])
1399
		$bpcfg['authserver'] = "dce-server";
1400
	if (!$bpcfg['authdomain'])
1401
		$bpcfg['authdomain'] = $defaultdomain;
1402

    
1403
	$bpconf = <<<EOD
1404
username {$bpcfg['username']}
1405
password {$bpcfg['password']}
1406
authserver {$bpcfg['authserver']}
1407
authdomain {$bpcfg['authdomain']}
1408
localport 5050
1409

    
1410
EOD;
1411

    
1412
	if ($bpcfg['minheartbeatinterval'])
1413
		$bpconf .= "minheartbeatinterval {$bpcfg['minheartbeatinterval']}\n";
1414

    
1415
	fwrite($fd, $bpconf);
1416
	fclose($fd);
1417

    
1418
	/* fire up bpalogin */
1419
	mwexec("/usr/local/sbin/bpalogin -c {$g['varetc_path']}/bpalogin.conf");
1420

    
1421
	return 0;
1422
}
1423

    
1424
function get_real_wan_interface() {
1425
	global $config, $g;
1426

    
1427
	$wancfg = $config['interfaces']['wan'];
1428

    
1429
	$wanif = $wancfg['if'];
1430
	if (($wancfg['ipaddr'] == "pppoe") || ($wancfg['ipaddr'] == "pptp")) {
1431
		$wanif = $g['pppoe_interface'];
1432
	}
1433

    
1434
	return $wanif;
1435
}
1436

    
1437
function get_current_wan_address($interface = "wan") {
1438
	global $config, $g;
1439

    
1440
	$wancfg = $config['interfaces'][$interface];
1441

    
1442
	$interface = filter_translate_type_to_real_interface($interface);
1443
	$ifinfo = "";
1444
	if(in_array($wancfg['ipaddr'], array('dhcp'))) {
1445
		/* get interface info with netstat */
1446
		exec("/usr/bin/netstat -nWI " . escapeshellarg($interface) . " -f inet", $ifinfo);
1447

    
1448
		if (isset($ifinfo[1])) {
1449
			$aif = preg_split("/\s+/", $ifinfo[1]);
1450
			$curwanip = chop($aif[3]);
1451

    
1452
			if ($curwanip && is_ipaddr($curwanip) && ($curwanip != "0.0.0.0"))
1453
				return $curwanip;
1454
		}
1455

    
1456
		return null;
1457
	} else if (in_array($wancfg['ipaddr'], array('pppoe','pptp','bigpond'))) {
1458
		/* dynamic WAN IP address, find out which one */
1459
		$wanif = get_real_wan_interface();
1460

    
1461
		/* get interface info with netstat */
1462
		exec("/usr/bin/netstat -nWI " . escapeshellarg($wanif) . " -f inet", $ifinfo);
1463

    
1464
		if (isset($ifinfo[1])) {
1465
			$aif = preg_split("/\s+/", $ifinfo[1]);
1466
			$curwanip = chop($aif[3]);
1467

    
1468
			if ($curwanip && is_ipaddr($curwanip) && ($curwanip != "0.0.0.0"))
1469
				return $curwanip;
1470
		}
1471

    
1472
		return null;
1473
	} else {
1474
		/* static WAN IP address */
1475
		return $wancfg['ipaddr'];
1476
	}
1477
}
1478

    
1479
/****f* interfaces/is_altq_capable
1480
 * NAME
1481
 *   is_altq_capable - Test if interface is capable of using ALTQ
1482
 * INPUTS
1483
 *   $int            - string containing interface name
1484
 * RESULT
1485
 *   boolean         - true or false
1486
 ******/
1487

    
1488
function is_altq_capable($int) {
1489
        /* Per:
1490
         * http://www.freebsd.org/cgi/man.cgi?query=altq&manpath=FreeBSD+6.0-current&format=html
1491
         * Only the following drivers have ALTQ support
1492
         */
1493
        $capable = array("an", "ath", "awi", "bfe", "bge", "dc", "de", "ed",
1494
		"em", "fxp", "hme", "lnc", "re", "rl", "ndis", "sf", "sis", "sk",
1495
		"tun", "vr", "wi", "xl", "vlan", "ste");
1496

    
1497
        $int_family = preg_split("/[0-9]+/", $int);
1498

    
1499
        if (in_array($int_family[0], $capable))
1500
                return true;
1501
        else
1502
                return false;
1503
}
1504

    
1505
function get_number_of_bridged_interfaces() {
1506
	$bridges_total = 0;
1507
	$bridges = split("\n", `/sbin/ifconfig -a | /usr/bin/grep bridge | grep flags`);
1508
	foreach($bridges as $bridge) {
1509
		$match_array = "";
1510
		preg_match_all("/bridge(.*):/",$bridge,$match_array);
1511
		if($match_array[1][0] <> "") {
1512
			if($match_array[1][0] > $bridges_total)
1513
				$bridges_total = $match_array[1][0];
1514
		}
1515
	}
1516
	return "{$bridges_total}";
1517
}
1518

    
1519
function get_next_available_bridge_interface() {
1520
	$bridges_total = get_number_of_bridged_interfaces();
1521
	$interfaces = `/sbin/ifconfig -l`;
1522
	$x=0;
1523
	for($x=0; $x<$bridges_total; $x++) {
1524
		if(!stristr($interfaces, "bridge{$x}")) {
1525
			return "{$x}";
1526
		}
1527
	}
1528
	return "{$x}";
1529
}
1530

    
1531
function destroy_bridge($bridge_num) {
1532
	mwexec("/sbin/ifconfig bridge{$bridge_num} down");
1533
	sleep(1);
1534
	mwexec("/sbin/ifconfig bridge{$bridge_num} delete");
1535
	sleep(1);
1536
	mwexec("/sbin/ifconfig bridge{$bridge_num} destroy");
1537
	sleep(1);
1538
	return;
1539
}
1540

    
1541
function discover_bridge($interface1, $interface2) {
1542
	if(!$interface1) return;
1543
	if(!$interface2) return;
1544
	$total_bridges = get_number_of_bridged_interfaces();
1545
	$total_bridges++;
1546
	$interfaces = `/sbin/ifconfig -l`;
1547
	$x=0;
1548
	for($x=0; $x<$total_bridges; $x++) {
1549
		$bridge_text = "NA";
1550
		if(!stristr($interfaces, "bridge{$x}"))
1551
			continue;
1552
		$bridge_text = `/sbin/ifconfig bridge{$x} | grep member`;
1553
		if(stristr($bridge_text, $interface1))
1554
			if(stristr($bridge_text, $interface2))
1555
				return $x;
1556
	}
1557
	return "-1";
1558
}
1559

    
1560
function get_wireless_modes($interface)
1561
{
1562
	/* return wireless modes and channels */
1563
	if(is_interface_wireless($interface)) {
1564
		$wi = 1;
1565
		$ifconfig = "/sbin/ifconfig";
1566
		$awk = "/usr/bin/awk";
1567
		$chan_list = "$ifconfig $interface list chan";
1568
		$stack_list = "$awk -F\"Channel \" '{ gsub(/\\*/, \" \"); print \$2 \"\\\n\" \$3 }'";
1569
		$format_list = "$awk '{print \$5 \" \" \$6 \",\" \$1}'";
1570

    
1571
		$interface_channels = "";
1572
		exec("$chan_list | $stack_list | sort -u | $format_list 2>&1", $interface_channels);
1573
		$interface_channel_count = count($interface_channels);
1574

    
1575
		$c = 0;
1576
		while ($c < $interface_channel_count)
1577
		{
1578
			$channel_line = explode(",", $interface_channels["$c"]);
1579
			$wireless_mode = trim($channel_line[0]);
1580
			$wireless_channel = trim($channel_line[1]);
1581
			if(trim($wireless_mode) != "") {
1582
				/* if we only have 11g also set 11b channels */
1583
				if($wireless_mode == "11g") {
1584
					$wireless_modes["11b"] = array();
1585
				}
1586
				$wireless_modes["$wireless_mode"]["$c"] = $wireless_channel;
1587
			}
1588
			$c++;
1589
		}
1590
	}
1591
	return($wireless_modes);
1592
}
1593

    
1594
?>
(10-10/27)