Project

General

Profile

Download (144 KB) Statistics
| Branch: | Tag: | Revision:
1 5b237745 Scott Ullrich
<?php
2
/*
3
	interfaces.inc
4 eba938e3 Scott Ullrich
	Copyright (C) 2004-2008 Scott Ullrich
5 a687f866 Namezero
	Copyright (C) 2008-2009 Ermal Lu?i
6 ac3f8318 Espen Johansen
	All rights reserved.
7
8
	function interfaces_wireless_configure is
9
	Copyright (C) 2005 Espen Johansen
10 cfc707f7 Scott Ullrich
	All rights reserved.
11
12
	originally part of m0n0wall (http://m0n0.ch/wall)
13 5b237745 Scott Ullrich
	Copyright (C) 2003-2004 Manuel Kasper <mk@neon1.net>.
14
	All rights reserved.
15 cfc707f7 Scott Ullrich
16 5b237745 Scott Ullrich
	Redistribution and use in source and binary forms, with or without
17
	modification, are permitted provided that the following conditions are met:
18 cfc707f7 Scott Ullrich
19 ac3f8318 Espen Johansen
	1. Redistributions of source code must retain the above copyright notices,
20 5b237745 Scott Ullrich
	   this list of conditions and the following disclaimer.
21 cfc707f7 Scott Ullrich
22 5b237745 Scott Ullrich
	2. Redistributions in binary form must reproduce the above copyright
23 ac3f8318 Espen Johansen
	   notices, this list of conditions and the following disclaimer in the
24 5b237745 Scott Ullrich
	   documentation and/or other materials provided with the distribution.
25 cfc707f7 Scott Ullrich
26 5b237745 Scott Ullrich
	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 523855b0 Scott Ullrich
37 b0c6a4f1 Ermal
	pfSense_BUILDER_BINARIES:	/sbin/dhclient	/bin/sh	/usr/bin/grep	/usr/bin/xargs	/usr/bin/awk	/usr/local/sbin/choparp
38 89c52814 Ermal
	pfSense_BUILDER_BINARIES:	/sbin/ifconfig	/sbin/route	/usr/sbin/ngctl	/usr/sbin/arp	/bin/kill	/usr/local/sbin/mpd5
39 d53a9a51 smos
	pfSense_BUILDER_BINARIES:	/usr/local/sbin/dhcp6c
40 523855b0 Scott Ullrich
	pfSense_MODULE:	interfaces
41
42 5b237745 Scott Ullrich
*/
43
44
/* include all configuration functions */
45 7387844e Chris Buechler
require_once("globals.inc");
46 9a456170 Darren Embry
require_once("util.inc");
47 36b2d82d smos
require_once("gwlb.inc");
48 5b237745 Scott Ullrich
49 b5b957fe Scott Ullrich
function interfaces_bring_up($interface) {
50
	if(!$interface) {
51 07e40c1f Carlos Eduardo Ramos
		log_error(gettext("interfaces_bring_up() was called but no variable defined."));
52 ec054b7c Scott Ullrich
		log_error( "Backtrace: " . debug_backtrace() );
53 b5b957fe Scott Ullrich
		return;
54
	}
55 871768cf Ermal
	pfSense_interface_flags($interface, IFF_UP);
56 b5b957fe Scott Ullrich
}
57
58 52947718 Ermal Lu?i
/*
59
 * Return the interface array
60
 */
61
function get_interface_arr($flush = false) {
62 1c3ddd9e Renato Botelho
	global $interface_arr_cache;
63 52947718 Ermal Lu?i
64 1c3ddd9e Renato Botelho
	/* If the cache doesn't exist, build it */
65
	if (!isset($interface_arr_cache) or $flush)
66
		$interface_arr_cache = pfSense_interface_listget();
67 52947718 Ermal Lu?i
68 1c3ddd9e Renato Botelho
	return $interface_arr_cache;
69 52947718 Ermal Lu?i
}
70
71
/*
72
 * does_interface_exist($interface): return true or false if a interface is
73
 * detected.
74
 */
75
function does_interface_exist($interface) {
76 8256f324 gnhb
	global $config;
77 be45aa79 Renato Botelho
78 8256f324 gnhb
	if(!$interface)
79 72993196 Ermal
		return false;
80 52947718 Ermal Lu?i
81 72993196 Ermal
	$ints = get_interface_arr(true);
82 6d5446a2 Ermal
	if (in_array($interface, $ints))
83 8256f324 gnhb
		return true;
84
	else
85
		return false;
86 52947718 Ermal Lu?i
}
87
88 2708a5cf Ermal
/*
89
 * does_vip_exist($vip): return true or false if a vip is
90
 * configured.
91
 */
92
function does_vip_exist($vip) {
93
	global $config;
94 be45aa79 Renato Botelho
95 2708a5cf Ermal
	if(!$vip)
96
		return false;
97
98
99 b526daaf Ermal
	switch ($vip['mode']) {
100 2708a5cf Ermal
	case "carp":
101 7b47bd4c Ermal
		$realif = "{$vip['interface']}_vip{$vip['vhid']}";
102 b526daaf Ermal
		if (!does_interface_exist($realif)) {
103
			return false;
104
		}
105
		break;
106 2708a5cf Ermal
	case "ipalias":
107 b526daaf Ermal
		$realif = get_real_interface($vip['interface']);
108
		if (!does_interface_exist($realif)) {
109
			return false;
110 2708a5cf Ermal
		}
111
		break;
112
	case "proxyarp":
113
		/* XXX: Implement this */
114 b526daaf Ermal
	default:
115
		return false;
116
	}
117
118
	$ifacedata = pfSense_getall_interface_addresses($realif);
119
	foreach ($ifacedata as $vipips) {
120
		if ($vipips == "{$vip['subnet']}/{$vip['subnet_bits']}")
121
			return true;
122 2708a5cf Ermal
	}
123
124
	return false;
125
}
126
127 67b057a9 Ermal
function interface_netgraph_needed($interface = "wan") {
128
	global $config;
129
130
	$found = false;
131
	if (!empty($config['pptpd']) &&
132
		$config['pptpd']['mode'] == "server")
133
		$found = true;
134
	if ($found == false && !empty($config['l2tp']) &&
135
		$config['l2tp']['mode'] == "server")
136
		$found = true;
137
	if ($found == false && is_array($config['pppoes']['pppoe'])) {
138
		foreach ($config['pppoes']['pppoe'] as $pppoe) {
139
			if ($pppoe['mode'] != "server")
140
				continue;
141
			if ($pppoe['interface'] == $interface)
142
				$found = true;
143
				break;
144
		}
145
	}
146 3dfc2d1a Ermal
	if ($found == false) {
147
		if (!empty($config['interfaces'][$interface])) {
148
			switch ($config['interfaces'][$interface]['ipaddr']) {
149
			case "ppp":
150
			case "pppoe":
151
			case "l2tp":
152
			case "pptp":
153
				$found = true;
154
				break;
155
			default:
156
				$found = false;
157
				break;
158
			}
159 9d7d2388 Ermal
		}
160
	}
161
	if ($found == false) {
162
		$realif = get_real_interface($interface);
163
		if (is_array($config['ppps']['ppp']) && count($config['ppps']['ppp'])) {
164
			foreach ($config['ppps']['ppp'] as $pppid => $ppp) {
165 20cb9803 gnhb
166
/* This if block doesn't do anything. It can be deleted.
167
PPP interfaces are found above in the previous if ($found == false) block.
168
This block of code is only entered for OPTx interfaces that are configured for PPPoE modem access, so $realif != $ppp['if']
169
170 9d7d2388 Ermal
				if ($realif == $ppp['if']) {
171
					$found = true;
172
					break;
173 3dfc2d1a Ermal
				}
174 be45aa79 Renato Botelho
*/
175 3eb00b49 gnhb
				$ports = explode(',',$ppp['ports']);
176
				foreach($ports as $pid => $port){
177 20cb9803 gnhb
					$port = get_real_interface($port);
178 3eb00b49 gnhb
					if ($realif == $port) {
179
						$found = true;
180
						break;
181
					}
182 be45aa79 Renato Botelho
					/* Find the parent interfaces of the vlans in the MLPPP configs
183
					* there should be only one element in the array here
184 20cb9803 gnhb
					* -- this could be better . . . */
185
					$parent_if = get_parent_interface($port);
186
					if ($realif == $parent_if[0]) {
187
						$found = true;
188
						break;
189
					}
190 3eb00b49 gnhb
				}
191 9d7d2388 Ermal
			}
192 67b057a9 Ermal
		}
193
	}
194 be45aa79 Renato Botelho
195 31eee4a6 Ermal
	if ($found == false) {
196
		$realif = get_real_interface($interface);
197 67b057a9 Ermal
		pfSense_ngctl_detach("{$realif}:", $realif);
198 31eee4a6 Ermal
	}
199 92a1c8e6 Ermal
	/* NOTE: We make sure for this on interface_ppps_configure()
200
	 *	no need to do it here agan.
201
	 *	else
202
	 *		pfSense_ngctl_attach(".", $realif);
203
	 */
204 67b057a9 Ermal
}
205
206 eba938e3 Scott Ullrich
function interfaces_loopback_configure() {
207 7734aea6 Andrew Thompson
	global $g;
208
209
	if ($g['platform'] == 'jail')
210
		return;
211 7a6f7c55 Scott Ullrich
	if($g['booting'])
212 07e40c1f Carlos Eduardo Ramos
		echo gettext("Configuring loopback interface...");
213 871768cf Ermal
	pfSense_interface_setaddress("lo0", "127.0.0.1");
214 b5b957fe Scott Ullrich
	interfaces_bring_up("lo0");
215 7a6f7c55 Scott Ullrich
	if($g['booting'])
216 07e40c1f Carlos Eduardo Ramos
		echo gettext("done.") . "\n";
217 5b237745 Scott Ullrich
	return 0;
218
}
219
220 eba938e3 Scott Ullrich
function interfaces_vlan_configure() {
221 7a6f7c55 Scott Ullrich
	global $config, $g;
222 87519eb7 Scott Ullrich
	if($g['booting'])
223 07e40c1f Carlos Eduardo Ramos
		echo gettext("Configuring VLAN interfaces...");
224 5b6eac01 Scott Ullrich
	if (is_array($config['vlans']['vlan']) && count($config['vlans']['vlan'])) {
225 e1c449c0 Ermal Lu?i
		foreach ($config['vlans']['vlan'] as $vlan) {
226 f620d00d Ermal Luçi
			if(empty($vlan['vlanif']))
227 48315e65 Ermal Luci
				$vlan['vlanif'] = "{$vlan['if']}_vlan{$vlan['tag']}";
228 5b6eac01 Scott Ullrich
			/* XXX: Maybe we should report any errors?! */
229 5f1e1d26 Ermal Lu?i
			interface_vlan_configure($vlan);
230 517feb1c Seth Mos
		}
231 5b6eac01 Scott Ullrich
	}
232 87519eb7 Scott Ullrich
	if($g['booting'])
233 07e40c1f Carlos Eduardo Ramos
		echo gettext("done.") . "\n";
234 2075fadb Ermal Luçi
}
235 cfc707f7 Scott Ullrich
236 abcb2bed Ermal Lu?i
function interface_vlan_configure(&$vlan) {
237 1c3ddd9e Renato Botelho
	global $config, $g;
238 161040eb Scott Ullrich
239 5f1e1d26 Ermal Lu?i
	if (!is_array($vlan)) {
240 07e40c1f Carlos Eduardo Ramos
		log_error(gettext("VLAN: called with wrong options. Problems with config!"));
241 5f1e1d26 Ermal Lu?i
		return;
242
	}
243
	$if = $vlan['if'];
244 48315e65 Ermal Luci
	$vlanif  = empty($vlan['vlanif']) ? "{$if}_vlan{$vlan['tag']}" : $vlan['vlanif'];
245 5f1e1d26 Ermal Lu?i
	$tag = $vlan['tag'];
246
247 871768cf Ermal
	if (empty($if)) {
248 905ea336 Phil Davis
		log_error(gettext("interface_vlan_configure called with if undefined."));
249 3ae4960c Ermal Luçi
		return;
250
	}
251
252 37a53d16 Scott Ullrich
	/* make sure the parent interface is up */
253 07101b63 Ermal Luçi
	interfaces_bring_up($if);
254
	/* Since we are going to add vlan(4) try to enable all that hardware supports. */
255 871768cf Ermal
	pfSense_interface_capabilities($if, IFCAP_VLAN_HWTAGGING|IFCAP_VLAN_MTU|IFCAP_VLAN_HWFILTER);
256 cfc707f7 Scott Ullrich
257 4aca19b3 Scott Ullrich
	if (!empty($vlanif) && does_interface_exist($vlanif)) {
258 df2a0f18 Ermal
		interface_bring_down($vlanif, true);
259 4aca19b3 Scott Ullrich
	} else {
260 871768cf Ermal
		$tmpvlanif = pfSense_interface_create("vlan");
261
		pfSense_interface_rename($tmpvlanif, $vlanif);
262
		pfSense_ngctl_name("{$tmpvlanif}:", $vlanif);
263 abcb2bed Ermal Lu?i
	}
264 871768cf Ermal
265
	pfSense_vlan_create($vlanif, $if, $tag);
266 2075fadb Ermal Luçi
267 07101b63 Ermal Luçi
	interfaces_bring_up($vlanif);
268 cfc707f7 Scott Ullrich
269 40b0b541 Ermal Lu?i
	/* invalidate interface cache */
270
	get_interface_arr(true);
271 3f7d2120 Bill Marquette
272 4aca19b3 Scott Ullrich
	/* XXX: ermal -- for now leave it here at the moment it does not hurt. */
273 07101b63 Ermal Luçi
	interfaces_bring_up($if);
274 cfc707f7 Scott Ullrich
275 4aca19b3 Scott Ullrich
	return $vlanif;
276 5b237745 Scott Ullrich
}
277
278 abcb2bed Ermal Lu?i
function interface_qinq_configure(&$vlan, $fd = NULL) {
279 1c3ddd9e Renato Botelho
	global $config, $g;
280
281
	if (!is_array($vlan)) {
282
		log_error(sprintf(gettext("QinQ compat VLAN: called with wrong options. Problems with config!%s"), "\n"));
283
		return;
284
	}
285
286
	$qinqif = $vlan['if'];
287
	$tag = $vlan['tag'];
288
	if(empty($qinqif)) {
289
		log_error(sprintf(gettext("interface_qinq_configure called with if undefined.%s"), "\n"));
290
		return;
291
	}
292 782e33f8 Renato Botelho
293
	if(!does_interface_exist($qinqif)) {
294
		log_error(sprintf(gettext("interface_qinq_configure called with invalid if.%s"), "\n"));
295
		return;
296
	}
297
298 4400ad66 Ermal Lu?i
	$vlanif = interface_vlan_configure($vlan);
299 5f1e1d26 Ermal Lu?i
300 1c3ddd9e Renato Botelho
	if ($fd == NULL) {
301
		$exec = true;
302
		$fd = fopen("{$g['tmp_path']}/netgraphcmd", "w");
303
	} else
304
		$exec = false;
305
	/* make sure the parent is converted to ng_vlan(4) and is up */
306
	interfaces_bring_up($qinqif);
307 5f1e1d26 Ermal Lu?i
308 9cf46050 Ermal
	pfSense_ngctl_attach(".", $qinqif);
309 1c3ddd9e Renato Botelho
	if (!empty($vlanif) && does_interface_exist($vlanif)) {
310
		fwrite($fd, "shutdown {$qinqif}qinq:\n");
311
		exec("/usr/sbin/ngctl msg {$qinqif}qinq: gettable", $result);
312
		if (empty($result)) {
313
			fwrite($fd, "mkpeer {$qinqif}: vlan lower downstream\n");
314
			fwrite($fd, "name {$qinqif}:lower {$vlanif}qinq\n");
315
			fwrite($fd, "connect {$qinqif}: {$vlanif}qinq: upper nomatch\n");
316
		}
317
	} else {
318
		fwrite($fd, "mkpeer {$qinqif}: vlan lower downstream\n");
319
		fwrite($fd, "name {$qinqif}:lower {$vlanif}qinq\n");
320
		fwrite($fd, "connect {$qinqif}: {$vlanif}qinq: upper nomatch\n");
321
	}
322
323
	/* invalidate interface cache */
324
	get_interface_arr(true);
325
326 76254caa Renato Botelho
	if (!stristr($qinqif, "_vlan"))
327 1c3ddd9e Renato Botelho
		mwexec("/sbin/ifconfig {$qinqif} promisc\n");
328
329
	$macaddr = get_interface_mac($qinqif);
330
	if (!empty($vlan['members'])) {
331
		$members = explode(" ", $vlan['members']);
332
		foreach ($members as $qtag) {
333
			$qinq = array();
334
			$qinq['tag'] = $qtag;
335
			$qinq['if'] = $vlanif;
336
			interface_qinq2_configure($qinq, $fd, $macaddr);
337
		}
338
	}
339
	if ($exec == true) {
340
		fclose($fd);
341
		mwexec("/usr/sbin/ngctl -f {$g['tmp_path']}/netgraphcmd");
342
	}
343
344
	interfaces_bring_up($qinqif);
345
	if (!empty($vlan['members'])) {
346
		$members = explode(" ", $vlan['members']);
347
		foreach ($members as $qif)
348
			interfaces_bring_up("{$vlanif}_{$qif}");
349
	}
350
351
	return $vlanif;
352 5f1e1d26 Ermal Lu?i
}
353
354
function interfaces_qinq_configure() {
355 7a6f7c55 Scott Ullrich
	global $config, $g;
356
	if($g['booting'])
357 07e40c1f Carlos Eduardo Ramos
		echo gettext("Configuring QinQ interfaces...");
358 7a6f7c55 Scott Ullrich
	if (is_array($config['qinqs']['qinqentry']) && count($config['qinqs']['qinqentry'])) {
359
		foreach ($config['qinqs']['qinqentry'] as $qinq) {
360
			/* XXX: Maybe we should report any errors?! */
361 4400ad66 Ermal Lu?i
			interface_qinq_configure($qinq);
362 7a6f7c55 Scott Ullrich
		}
363 4400ad66 Ermal Lu?i
	}
364
	if($g['booting'])
365 07e40c1f Carlos Eduardo Ramos
		echo gettext( "done.") . "\n";
366 5f1e1d26 Ermal Lu?i
}
367
368 abcb2bed Ermal Lu?i
function interface_qinq2_configure(&$qinq, $fd, $macaddr) {
369 1c3ddd9e Renato Botelho
	global $config, $g;
370
371
	if (!is_array($qinq)) {
372
		log_error(sprintf(gettext("QinQ compat VLAN: called with wrong options. Problems with config!%s"), "\n"));
373
		return;
374
	}
375
376
	$if = $qinq['if'];
377
	$tag = $qinq['tag'];
378
	$vlanif = "{$if}_{$tag}";
379
	if(empty($if)) {
380
		log_error(sprintf(gettext("interface_qinq2_configure called with if undefined.%s"), "\n"));
381
		return;
382
	}
383
384
	fwrite($fd, "shutdown {$if}h{$tag}:\n");
385
	fwrite($fd, "mkpeer {$if}qinq: eiface {$if}{$tag} ether\n");
386
	fwrite($fd, "name {$if}qinq:{$if}{$tag} {$if}h{$tag}\n");
387
	fwrite($fd, "msg {$if}qinq: addfilter { vlan={$tag} hook=\"{$if}{$tag}\" }\n");
388
	fwrite($fd, "msg {$if}h{$tag}: setifname \"{$vlanif}\"\n");
389
	fwrite($fd, "msg {$if}h{$tag}: set {$macaddr}\n");
390
391
	/* invalidate interface cache */
392
	get_interface_arr(true);
393
394
	return $vlanif;
395 5f1e1d26 Ermal Lu?i
}
396
397 9f428275 Erik Fonnesbeck
function interfaces_create_wireless_clones() {
398 7bb09580 Erik Fonnesbeck
	global $config, $g;
399 9f428275 Erik Fonnesbeck
400
	if($g['booting'])
401 7bb09580 Erik Fonnesbeck
		echo gettext("Creating wireless clone interfaces...");
402
403
	$iflist = get_configured_interface_list();
404
405 0fbf7315 Ermal
	foreach ($iflist as $if) {
406 7bb09580 Erik Fonnesbeck
		$realif = $config['interfaces'][$if]['if'];
407
		if (is_interface_wireless($realif))
408
			interface_wireless_clone(interface_get_wireless_clone($realif), $config['interfaces'][$if]);
409
	}
410
411 6ef2297b Erik Fonnesbeck
	if (isset($config['wireless']['clone']) && is_array($config['wireless']['clone']) && count($config['wireless']['clone'])) {
412 9f428275 Erik Fonnesbeck
		foreach ($config['wireless']['clone'] as $clone) {
413
			if(empty($clone['cloneif']))
414
				continue;
415
			if(does_interface_exist($clone['cloneif']))
416
				continue;
417
			/* XXX: Maybe we should report any errors?! */
418 7bb09580 Erik Fonnesbeck
			interface_wireless_clone($clone['cloneif'], $clone);
419 9f428275 Erik Fonnesbeck
		}
420
	}
421
	if($g['booting'])
422 7bb09580 Erik Fonnesbeck
		echo gettext("done.") . "\n";
423 a687f866 Namezero
424 9f428275 Erik Fonnesbeck
}
425
426 d7f1891b Ermal
function interfaces_bridge_configure($checkmember = 0) {
427 1c3ddd9e Renato Botelho
	global $config;
428
429
	$i = 0;
430
	if (is_array($config['bridges']['bridged']) && count($config['bridges']['bridged'])) {
431
		foreach ($config['bridges']['bridged'] as $bridge) {
432
			if(empty($bridge['bridgeif']))
433
				$bridge['bridgeif'] = "bridge{$i}";
434 ef1c048b Ermal
			if ($checkmember == 1) {
435
				$members = explode(',', $bridge['members']);
436
				foreach ($members as $member) {
437
					if (strstr($bridge['if'], "_vip"))
438
						continue 2;
439
					if (!empty($config['interfaces'][$bridge['if']]) && $config['interfaces'][$bridge['if']]['ipaddrv6'] == "track6")  
440
						continue 2;
441
				}
442
			}
443
			else if ($checkmember == 2) {
444
				$members = explode(',', $bridge['members']);
445
				foreach ($members as $member) {
446
					if (!strstr($bridge['if'], "_vip"))
447
						continue 2;
448
					if (empty($config['interfaces'][$bridge['if']]) || $config['interfaces'][$bridge['if']]['ipaddrv6'] != "track6")  
449
						continue 2;
450
				}
451
			}
452 1c3ddd9e Renato Botelho
			/* XXX: Maybe we should report any errors?! */
453
			interface_bridge_configure($bridge, $checkmember);
454
			$i++;
455
		}
456
	}
457 bad29bc6 Ermal Luçi
}
458
459 02de5c07 Ermal
function interface_bridge_configure(&$bridge, $checkmember = 0) {
460 d7147b1c Scott Ullrich
	global $config, $g;
461 bad29bc6 Ermal Luçi
462 d7147b1c Scott Ullrich
	if (!is_array($bridge))
463 0e0002c2 bcyrill
		return;
464 bad29bc6 Ermal Luçi
465 dc97efaf Ermal Luçi
	if (empty($bridge['members'])) {
466 07e40c1f Carlos Eduardo Ramos
		log_error(sprintf(gettext("No members found on %s"), $bridge['bridgeif']));
467 0e0002c2 bcyrill
		return;
468 dc97efaf Ermal Luçi
	}
469
470 bad29bc6 Ermal Luçi
	$members = explode(',', $bridge['members']);
471 70720671 Ermal Luçi
	if (!count($members))
472 0e0002c2 bcyrill
		return;
473 ea5f6c95 Ermal
474 b64523c1 Ermal Luçi
	/* Calculate smaller mtu and enforce it */
475 69e53ef0 Ermal Luçi
	$smallermtu = 0;
476 07676e36 Ermal
	$commonrx = true;
477
	$commontx = true;
478 02de5c07 Ermal
	$foundgif = false;
479 b64523c1 Ermal Luçi
	foreach ($members as $member) {
480
		$realif = get_real_interface($member);
481 07676e36 Ermal
		$opts = pfSense_get_interface_addresses($realif);
482
		$mtu = $opts['mtu'];
483 02de5c07 Ermal
		if (substr($realif, 0, 3) == "gif") {
484
			$foundgif = true;
485
			if ($checkmember == 1)
486
				return;
487
			if ($mtu <= 1500)
488
				continue;
489
		}
490 07676e36 Ermal
		if (!isset($opts['encaps']['txcsum']))
491
			$commontx = false;
492
		if (!isset($opts['encaps']['rxcsum']))
493
			$commonrx = false;
494 0ac206f9 Ermal
		if (!isset($opts['encaps']['tso4']))
495
			$commontso4 = false;
496
		if (!isset($opts['encaps']['tso6']))
497
			$commontso6 = false;
498
		if (!isset($opts['encaps']['lro']))
499
			$commonlro = false;
500 69e53ef0 Ermal Luçi
		if ($smallermtu == 0 && !empty($mtu))
501
			$smallermtu = $mtu;
502
		else if (!empty($mtu) && $mtu < $smallermtu)
503 b64523c1 Ermal Luçi
			$smallermtu = $mtu;
504
	}
505 02de5c07 Ermal
	if ($foundgif == false && $checkmember == 2)
506
		return;
507
508 69e53ef0 Ermal Luçi
	/* Just in case anything is not working well */
509
	if ($smallermtu == 0)
510 be45aa79 Renato Botelho
		$smallermtu = 1500;
511 69e53ef0 Ermal Luçi
512 07676e36 Ermal
	$flags = 0;
513 0ac206f9 Ermal
	if ($commonrx === false)
514 07676e36 Ermal
		$flags |= IFCAP_RXCSUM;
515 0ac206f9 Ermal
	if ($commontx === false)
516 07676e36 Ermal
		$flags |= IFCAP_TXCSUM;
517 0ac206f9 Ermal
	if ($commontso4 === false)
518
		$flags |= IFCAP_TSO4;
519
	if ($commontso6 === false)
520
		$flags |= IFCAP_TSO6;
521
	if ($commonlro === false)
522
		$flags |= IFCAP_LRO;
523 02de5c07 Ermal
524
	if ($g['booting'] || !empty($bridge['bridgeif'])) {
525
		pfSense_interface_destroy($bridge['bridgeif']);
526
		pfSense_interface_create($bridge['bridgeif']);
527 b3af5453 Renato Botelho
		$bridgeif = escapeshellarg($bridge['bridgeif']);
528 6d53bbb5 Ermal
	} else {
529 02de5c07 Ermal
		$bridgeif = pfSense_interface_create("bridge");
530 6d53bbb5 Ermal
		$bridge['bridgeif'] = $bridgeif;
531
	}
532 02de5c07 Ermal
533
	$checklist = get_configured_interface_list();
534
535 bad29bc6 Ermal Luçi
	/* Add interfaces to bridge */
536 31241000 Ermal Luçi
	foreach ($members as $member) {
537 19defb88 Ermal
		if (empty($checklist[$member]))
538 d7147b1c Scott Ullrich
			continue;
539 19defb88 Ermal
		$realif = get_real_interface($member);
540 07676e36 Ermal
		if (!$realif) {
541 07e40c1f Carlos Eduardo Ramos
			log_error(gettext("realif not defined in interfaces bridge - up"));
542 07676e36 Ermal
			continue;
543
		}
544
		/* make sure the parent interface is up */
545 19defb88 Ermal
		pfSense_interface_mtu($realif, $smallermtu);
546
		pfSense_interface_capabilities($realif, -$flags);
547
		interfaces_bring_up($realif);
548 6d53bbb5 Ermal
		pfSense_bridge_add_member($bridge['bridgeif'], $realif);
549 d7147b1c Scott Ullrich
	}
550 31241000 Ermal Luçi
551 bad29bc6 Ermal Luçi
	if (isset($bridge['enablestp'])) {
552
		/* Choose spanning tree proto */
553 b3af5453 Renato Botelho
		mwexec("/sbin/ifconfig {$bridgeif} proto " . escapeshellarg($bridge['proto']));
554 be45aa79 Renato Botelho
555 dc97efaf Ermal Luçi
		if (!empty($bridge['stp'])) {
556
			$stpifs = explode(',', $bridge['stp']);
557
			foreach ($stpifs as $stpif) {
558
				$realif = get_real_interface($stpif);
559
				mwexec("/sbin/ifconfig {$bridgeif} stp {$realif}");
560
			}
561 bad29bc6 Ermal Luçi
		}
562 dc97efaf Ermal Luçi
		if (!empty($bridge['maxage']))
563 b3af5453 Renato Botelho
			mwexec("/sbin/ifconfig {$bridgeif} maxage " . escapeshellarg($bridge['maxage']));
564 a5571287 Chris Buechler
		if (!empty($bridge['fwdelay']))
565 b3af5453 Renato Botelho
			mwexec("/sbin/ifconfig {$bridgeif} fwddelay " . escapeshellarg($bridge['fwdelay']));
566 a5571287 Chris Buechler
		if (!empty($bridge['hellotime']))
567 b3af5453 Renato Botelho
			mwexec("/sbin/ifconfig {$bridgeif} hellotime " . escapeshellarg($bridge['hellotime']));
568 a5571287 Chris Buechler
		if (!empty($bridge['priority']))
569 b3af5453 Renato Botelho
			mwexec("/sbin/ifconfig {$bridgeif} priority " . escapeshellarg($bridge['priority']));
570 afd825a7 bcyrill
		if (!empty($bridge['holdcnt']))
571 b3af5453 Renato Botelho
			mwexec("/sbin/ifconfig {$bridgeif} holdcnt " . escapeshellarg($bridge['holdcnt']));
572 dc97efaf Ermal Luçi
		if (!empty($bridge['ifpriority'])) {
573
			$pconfig = explode(",", $bridge['ifpriority']);
574
			$ifpriority = array();
575
			foreach ($pconfig as $cfg) {
576 9a456170 Darren Embry
				$embcfg = explode_assoc(":", $cfg);
577 dc97efaf Ermal Luçi
				foreach ($embcfg as $key => $value)
578
					$ifpriority[$key] = $value;
579
			}
580
			foreach ($ifpriority as $key => $value) {
581
				$realif = get_real_interface($key);
582 b3af5453 Renato Botelho
				mwexec("/sbin/ifconfig ${bridgeif} ifpriority {$realif} " . escapeshellarg($value));
583 dc97efaf Ermal Luçi
			}
584 bad29bc6 Ermal Luçi
		}
585 dc97efaf Ermal Luçi
		if (!empty($bridge['ifpathcost'])) {
586 da5895bb Darren Embry
			$pconfig = explode(",", $bridge['ifpathcost']);
587 dc97efaf Ermal Luçi
			$ifpathcost = array();
588
			foreach ($pconfig as $cfg) {
589 9a456170 Darren Embry
				$embcfg = explode_assoc(":", $cfg);
590 dc97efaf Ermal Luçi
				foreach ($embcfg as $key => $value)
591
					$ifpathcost[$key] = $value;
592
			}
593
			foreach ($ifpathcost as $key => $value) {
594 1c3ddd9e Renato Botelho
				$realif = get_real_interface($key);
595 b3af5453 Renato Botelho
				mwexec("/sbin/ifconfig ${bridgeif} ifpathcost {$realif} " . escapeshellarg($value));
596 1c3ddd9e Renato Botelho
			}
597 bad29bc6 Ermal Luçi
		}
598
	}
599
600
	if ($bridge['maxaddr'] <> "")
601
		mwexec("/sbin/ifconfig {$bridgeif} maxaddr {$bridge['maxaddr']}");
602 1c3ddd9e Renato Botelho
	if ($bridge['timeout'] <> "")
603
		mwexec("/sbin/ifconfig {$bridgeif} timeout {$bridge['timeout']}");
604
	if ($bridge['span'] <> "") {
605 85a5da13 Ermal Luçi
		$realif = get_real_interface($bridge['span']);
606 1c3ddd9e Renato Botelho
		mwexec("/sbin/ifconfig {$bridgeif} span {$realif}");
607 bad29bc6 Ermal Luçi
	}
608 a47a5798 Ermal Luçi
	if (!empty($bridge['edge'])) {
609 1c3ddd9e Renato Botelho
		$edgeifs = explode(',', $bridge['edge']);
610
		foreach ($edgeifs as $edgeif) {
611 a47a5798 Ermal Luçi
			$realif = get_real_interface($edgeif);
612 1c3ddd9e Renato Botelho
			mwexec("/sbin/ifconfig {$bridgeif} edge {$realif}");
613
		}
614 a47a5798 Ermal Luçi
	}
615
	if (!empty($bridge['autoedge'])) {
616 1c3ddd9e Renato Botelho
		$edgeifs = explode(',', $bridge['autoedge']);
617
		foreach ($edgeifs as $edgeif) {
618
			$realif = get_real_interface($edgeif);
619
			mwexec("/sbin/ifconfig {$bridgeif} -autoedge {$realif}");
620
		}
621 a47a5798 Ermal Luçi
	}
622
	if (!empty($bridge['ptp'])) {
623 1c3ddd9e Renato Botelho
		$ptpifs = explode(',', $bridge['ptp']);
624
		foreach ($ptpifs as $ptpif) {
625
			$realif = get_real_interface($ptpif);
626
			mwexec("/sbin/ifconfig {$bridgeif} ptp {$realif}");
627
		}
628 a47a5798 Ermal Luçi
	}
629
	if (!empty($bridge['autoptp'])) {
630 1c3ddd9e Renato Botelho
		$ptpifs = explode(',', $bridge['autoptp']);
631
		foreach ($ptpifs as $ptpif) {
632
			$realif = get_real_interface($ptpif);
633
			mwexec("/sbin/ifconfig {$bridgeif} -autoptp {$realif}");
634
		}
635 a47a5798 Ermal Luçi
	}
636
	if (!empty($bridge['static'])) {
637 1c3ddd9e Renato Botelho
		$stickyifs = explode(',', $bridge['static']);
638
		foreach ($stickyifs as $stickyif) {
639
			$realif = get_real_interface($stickyif);
640
			mwexec("/sbin/ifconfig {$bridgeif} sticky {$realif}");
641
		}
642 a47a5798 Ermal Luçi
	}
643
	if (!empty($bridge['private'])) {
644 1c3ddd9e Renato Botelho
		$privateifs = explode(',', $bridge['private']);
645
		foreach ($privateifs as $privateif) {
646
			$realif = get_real_interface($privateif);
647
			mwexec("/sbin/ifconfig {$bridgeif} private {$realif}");
648
		}
649 a47a5798 Ermal Luçi
	}
650 bad29bc6 Ermal Luçi
651 792bdf7f bcyrill
	if ($bridge['bridgeif'])
652 6d53bbb5 Ermal
		interfaces_bring_up($bridge['bridgeif']);
653 be45aa79 Renato Botelho
	else
654 07e40c1f Carlos Eduardo Ramos
		log_error(gettext("bridgeif not defined -- could not bring interface up"));
655 bad29bc6 Ermal Luçi
}
656
657 fcd4a425 Ermal Lu?i
function interface_bridge_add_member($bridgeif, $interface) {
658
659
	if (!does_interface_exist($bridgeif) || !does_interface_exist($interface))
660
		return;
661
662 a5571287 Chris Buechler
	$mtu = get_interface_mtu($bridgeif);
663 fcd4a425 Ermal Lu?i
	$mtum = get_interface_mtu($interface);
664 be45aa79 Renato Botelho
665 73481ad3 Ermal
	if ($mtu != $mtum && !(substr($interface, 0, 3) == "gif" && $mtu <= 1500))
666 871768cf Ermal
		pfSense_interface_mtu($interface, $mtu);
667 fcd4a425 Ermal Lu?i
668 0c77c314 Ermal
	$options = pfSense_get_interface_addresses($bridgeif);
669 51d5aad7 Ermal
	$flags = 0;
670
	if (!isset($options['encaps']['txcsum']))
671
		$flags |= IFCAP_TXCSUM;
672 ea5f6c95 Ermal
673 51d5aad7 Ermal
	if (!isset($options['encaps']['rxcsum']))
674
		$flags |= IFCAP_RXCSUM;
675
676
	pfSense_interface_capabilities($interface, -$flags);
677 3ca774ac Ermal
678 fcd4a425 Ermal Lu?i
	interfaces_bring_up($interface);
679 2064fa2e Ermal
	pfSense_bridge_add_member($bridgeif, $interface);
680 fcd4a425 Ermal Lu?i
}
681
682 1c3ddd9e Renato Botelho
function interfaces_lagg_configure() {
683
	global $config, $g;
684
	if($g['booting'])
685
		echo gettext("Configuring LAGG interfaces...");
686
	$i = 0;
687
	if (is_array($config['laggs']['lagg']) && count($config['laggs']['lagg'])) {
688
		foreach ($config['laggs']['lagg'] as $lagg) {
689
			if(empty($lagg['laggif']))
690
				$lagg['laggif'] = "lagg{$i}";
691
			/* XXX: Maybe we should report any errors?! */
692
			interface_lagg_configure($lagg);
693
			$i++;
694 7a6f7c55 Scott Ullrich
		}
695 1c3ddd9e Renato Botelho
	}
696
	if($g['booting'])
697
		echo gettext("done.") . "\n";
698 cccf624b Ermal Luçi
}
699
700 eba938e3 Scott Ullrich
function interface_lagg_configure(&$lagg) {
701 1c3ddd9e Renato Botelho
	global $config, $g;
702 cccf624b Ermal Luçi
703 1c3ddd9e Renato Botelho
	if (!is_array($lagg))
704 cccf624b Ermal Luçi
		return -1;
705
706
	$members = explode(',', $lagg['members']);
707
	if (!count($members))
708
		return -1;
709 be45aa79 Renato Botelho
710 b64523c1 Ermal Luçi
	if ($g['booting'] || !(empty($lagg['laggif']))) {
711 871768cf Ermal
		pfSense_interface_destroy($lagg['laggif']);
712
		pfSense_interface_create($lagg['laggif']);
713 1c3ddd9e Renato Botelho
		$laggif = $lagg['laggif'];
714
	} else
715 871768cf Ermal
		$laggif = pfSense_interface_create("lagg");
716 b64523c1 Ermal Luçi
717
	/* Calculate smaller mtu and enforce it */
718 1c3ddd9e Renato Botelho
	$smallermtu = 0;
719
	foreach ($members as $member) {
720 0ac206f9 Ermal
		$opts = pfSense_get_interface_addresses($member);
721 1c3ddd9e Renato Botelho
		$mtu = $opts['mtu'];
722 0ac206f9 Ermal
		if (!isset($opts['encaps']['txcsum']))
723 1c3ddd9e Renato Botelho
			$commontx = false;
724
		if (!isset($opts['encaps']['rxcsum']))
725
			$commonrx = false;
726 0ac206f9 Ermal
		if (!isset($opts['encaps']['tso4']))
727
			$commontso4 = false;
728
		if (!isset($opts['encaps']['tso6']))
729
			$commontso6 = false;
730
		if (!isset($opts['encaps']['lro']))
731
			$commonlro = false;
732 69e53ef0 Ermal Luçi
		if ($smallermtu == 0 && !empty($mtu))
733
			$smallermtu = $mtu;
734 1c3ddd9e Renato Botelho
		else if (!empty($mtu) && $mtu < $smallermtu)
735
			$smallermtu = $mtu;
736
	}
737 b64523c1 Ermal Luçi
738 69e53ef0 Ermal Luçi
	/* Just in case anything is not working well */
739 1c3ddd9e Renato Botelho
	if ($smallermtu == 0)
740
		$smallermtu = 1500;
741 69e53ef0 Ermal Luçi
742 0ac206f9 Ermal
	$flags = 0;
743 1c3ddd9e Renato Botelho
	if ($commonrx === false)
744
		$flags |= IFCAP_RXCSUM;
745
	if ($commontx === false)
746
		$flags |= IFCAP_TXCSUM;
747 0ac206f9 Ermal
	if ($commontso4 === false)
748 1c3ddd9e Renato Botelho
		$flags |= IFCAP_TSO4;
749
	if ($commontso6 === false)
750
		$flags |= IFCAP_TSO6;
751
	if ($commonlro === false)
752
		$flags |= IFCAP_LRO;
753 0ac206f9 Ermal
754 02de5c07 Ermal
	$checklist = get_interface_list();
755
756 cccf624b Ermal Luçi
	foreach ($members as $member) {
757
		if (!array_key_exists($member, $checklist))
758
			continue;
759 d7147b1c Scott Ullrich
		/* make sure the parent interface is up */
760 871768cf Ermal
		pfSense_interface_mtu($member, $smallermtu);
761 0ac206f9 Ermal
		pfSense_interface_capabilities($member, -$flags);
762 39fbee97 Ermal Lu?i
		interfaces_bring_up($member);
763 f421cbcc Ermal Lu?i
		mwexec("/sbin/ifconfig {$laggif} laggport {$member}");
764 cccf624b Ermal Luçi
	}
765 be45aa79 Renato Botelho
766 39fbee97 Ermal Lu?i
	mwexec("/sbin/ifconfig {$laggif} laggproto {$lagg['proto']}");
767 acc1e9d0 Scott Ullrich
768 b5b957fe Scott Ullrich
	interfaces_bring_up($laggif);
769 cccf624b Ermal Luçi
770 d7147b1c Scott Ullrich
	return $laggif;
771 cccf624b Ermal Luçi
}
772
773 d7f1891b Ermal
function interfaces_gre_configure($checkparent = 0) {
774 1c3ddd9e Renato Botelho
	global $config;
775 582d2452 Ermal Luçi
776 1c3ddd9e Renato Botelho
	if (is_array($config['gres']['gre']) && count($config['gres']['gre'])) {
777
		foreach ($config['gres']['gre'] as $i => $gre) {
778
			if(empty($gre['greif']))
779
				$gre['greif'] = "gre{$i}";
780 ef1c048b Ermal
			if ($checkparent == 1) {
781
				if (strstr($gre['if'], "_vip"))
782
					continue;
783
				if (!empty($config['interfaces'][$gre['if']]) && $config['interfaces'][$gre['if']]['ipaddrv6'] == "track6")  
784
					continue;
785
			}
786
			else if ($checkparent == 2) {
787
				if (!strstr($gre['if'], "_vip"))
788
					continue;
789
				if (empty($config['interfaces'][$gre['if']]) || $config['interfaces'][$gre['if']]['ipaddrv6'] != "track6")  
790
					continue;
791
			}
792 1c3ddd9e Renato Botelho
			/* XXX: Maybe we should report any errors?! */
793
			interface_gre_configure($gre);
794
		}
795
	}
796 582d2452 Ermal Luçi
}
797
798 ed62880b Ermal
/* NOTE: $grekey is not used but useful for passing this function to array_walk. */
799
function interface_gre_configure(&$gre, $grekey = "") {
800 1c3ddd9e Renato Botelho
	global $config, $g;
801 582d2452 Ermal Luçi
802
	if (!is_array($gre))
803
		return -1;
804
805 85a5da13 Ermal Luçi
	$realif = get_real_interface($gre['if']);
806
	$realifip = get_interface_ip($gre['if']);
807 582d2452 Ermal Luçi
808 d7147b1c Scott Ullrich
	/* make sure the parent interface is up */
809 b5b957fe Scott Ullrich
	interfaces_bring_up($realif);
810 582d2452 Ermal Luçi
811 d7147b1c Scott Ullrich
	if ($g['booting'] || !(empty($gre['greif']))) {
812 871768cf Ermal
		pfSense_interface_destroy($gre['greif']);
813
		pfSense_interface_create($gre['greif']);
814 582d2452 Ermal Luçi
		$greif = $gre['greif'];
815 871768cf Ermal
	} else
816
		$greif = pfSense_interface_create("gre");
817 582d2452 Ermal Luçi
818
	/* Do not change the order here for more see gre(4) NOTES section. */
819
	mwexec("/sbin/ifconfig {$greif} tunnel {$realifip} {$gre['remote-addr']}");
820 a59c7fa6 smos
	if((is_ipaddrv6($gre['tunnel-local-addr'])) || (is_ipaddrv6($gre['tunnel-remote-addr']))) {
821
		mwexec("/sbin/ifconfig {$greif} inet6 {$gre['tunnel-local-addr']} {$gre['tunnel-remote-addr']} prefixlen /{$gre['tunnel-remote-net']} ");
822
	} else {
823 bfede3d4 jim-p
		mwexec("/sbin/ifconfig {$greif} {$gre['tunnel-local-addr']} {$gre['tunnel-remote-addr']} netmask " . gen_subnet_mask($gre['tunnel-remote-net']));
824 a59c7fa6 smos
	}
825 f8edf05d jim-p
	if (isset($gre['link0']))
826 871768cf Ermal
		pfSense_interface_flags($greif, IFF_LINK0);
827 f8edf05d jim-p
	if (isset($gre['link1']))
828 871768cf Ermal
		pfSense_interface_flags($greif, IFF_LINK1);
829 f8edf05d jim-p
	if (isset($gre['link2']))
830 871768cf Ermal
		pfSense_interface_flags($greif, IFF_LINK2);
831 d7147b1c Scott Ullrich
832
	if($greif)
833 b5b957fe Scott Ullrich
		interfaces_bring_up($greif);
834 be45aa79 Renato Botelho
	else
835 07e40c1f Carlos Eduardo Ramos
		log_error(gettext("Could not bring greif up -- variable not defined."));
836 582d2452 Ermal Luçi
837 53b0d9d3 Ermal Lu?i
	if (isset($gre['link1']) && $gre['link1'])
838 61b67ab3 Ermal Lu?i
		mwexec("/sbin/route add {$gre['tunnel-remote-addr']}/{$gre['tunnel-remote-net']} {$gre['tunnel-local-addr']}");
839 283e9180 Seth Mos
	if(is_ipaddrv4($gre['tunnel-remote-addr']))
840
		file_put_contents("{$g['tmp_path']}/{$greif}_router", $gre['tunnel-remote-addr']);
841
	if(is_ipaddrv6($gre['tunnel-remote-addr']))
842
		file_put_contents("{$g['tmp_path']}/{$greif}_routerv6", $gre['tunnel-remote-addr']);
843 582d2452 Ermal Luçi
844
	return $greif;
845
}
846
847 d7f1891b Ermal
function interfaces_gif_configure($checkparent = 0) {
848 9006e9f8 Scott Ullrich
	global $config;
849 f1a93dee Ermal
850 9006e9f8 Scott Ullrich
	if (is_array($config['gifs']['gif']) && count($config['gifs']['gif'])) {
851 f1a93dee Ermal
		foreach ($config['gifs']['gif'] as $i => $gif) {
852 9006e9f8 Scott Ullrich
			if(empty($gif['gifif']))
853
				$gre['gifif'] = "gif{$i}";
854 ef1c048b Ermal
			if ($checkparent == 1) {
855
				if (strstr($gif['if'], "_vip"))
856
					continue;
857
				if (!empty($config['interfaces'][$gif['if']]) && $config['interfaces'][$gif['if']]['ipaddrv6'] == "track6")  
858
					continue;
859
			}
860
			else if ($checkparent == 2) {
861
				if (!strstr($gre['if'], "_vip"))
862
					continue;
863
				if (empty($config['interfaces'][$gif['if']]) || $config['interfaces'][$gif['if']]['ipaddrv6'] != "track6")  
864
					continue;
865
			}
866 9006e9f8 Scott Ullrich
			/* XXX: Maybe we should report any errors?! */
867
			interface_gif_configure($gif);
868
		}
869
	}
870 582d2452 Ermal Luçi
}
871
872 ed62880b Ermal
/* NOTE: $gifkey is not used but useful for passing this function to array_walk. */
873
function interface_gif_configure(&$gif, $gifkey = "") {
874 9006e9f8 Scott Ullrich
	global $config, $g;
875 582d2452 Ermal Luçi
876 9006e9f8 Scott Ullrich
	if (!is_array($gif))
877
		return -1;
878 582d2452 Ermal Luçi
879 9006e9f8 Scott Ullrich
	$realif = get_real_interface($gif['if']);
880 8436caa7 bcyrill
	$ipaddr = $gif['ipaddr'];
881 582d2452 Ermal Luçi
882 8436caa7 bcyrill
	if (is_ipaddrv4($gif['remote-addr'])) {
883
		if (is_ipaddrv4($ipaddr))
884
			$realifip = $ipaddr;
885
		else
886
			$realifip = get_interface_ip($gif['if']);
887 01a58d89 smos
		$realifgw = get_interface_gateway($gif['if']);
888 8436caa7 bcyrill
	} else if (is_ipaddrv6($gif['remote-addr'])) {
889
		if (is_ipaddrv6($ipaddr))
890
			$realifip = $ipaddr;
891
		else
892
			$realifip = get_interface_ipv6($gif['if']);
893 01a58d89 smos
		$realifgw = get_interface_gatewayv6($gif['if']);
894
	}
895 9006e9f8 Scott Ullrich
	/* make sure the parent interface is up */
896
	if($realif)
897
		interfaces_bring_up($realif);
898 be45aa79 Renato Botelho
	else
899 07e40c1f Carlos Eduardo Ramos
		log_error(gettext("could not bring realif up -- variable not defined -- interface_gif_configure()"));
900 582d2452 Ermal Luçi
901 9006e9f8 Scott Ullrich
	if ($g['booting'] || !(empty($gif['gifif']))) {
902 871768cf Ermal
		pfSense_interface_destroy($gif['gifif']);
903
		pfSense_interface_create($gif['gifif']);
904 9006e9f8 Scott Ullrich
		$gifif = $gif['gifif'];
905
	} else
906 871768cf Ermal
		$gifif = pfSense_interface_create("gif");
907 9006e9f8 Scott Ullrich
908
	/* Do not change the order here for more see gif(4) NOTES section. */
909
	mwexec("/sbin/ifconfig {$gifif} tunnel {$realifip} {$gif['remote-addr']}");
910 9b1ff028 Seth Mos
	if((is_ipaddrv6($gif['tunnel-local-addr'])) || (is_ipaddrv6($gif['tunnel-remote-addr']))) {
911 5a8371cd smos
		mwexec("/sbin/ifconfig {$gifif} inet6 {$gif['tunnel-local-addr']} {$gif['tunnel-remote-addr']} prefixlen /{$gif['tunnel-remote-net']} ");
912 9b1ff028 Seth Mos
	} else {
913
		mwexec("/sbin/ifconfig {$gifif} {$gif['tunnel-local-addr']} {$gif['tunnel-remote-addr']} netmask " . gen_subnet_mask($gif['tunnel-remote-net']));
914
	}
915 f8edf05d jim-p
	if (isset($gif['link0']))
916 871768cf Ermal
		pfSense_interface_flags($gifif, IFF_LINK0);
917 f8edf05d jim-p
	if (isset($gif['link1']))
918 871768cf Ermal
		pfSense_interface_flags($gifif, IFF_LINK1);
919 9006e9f8 Scott Ullrich
	if($gifif)
920
		interfaces_bring_up($gifif);
921
	else
922 07e40c1f Carlos Eduardo Ramos
		log_error(gettext("could not bring gifif up -- variable not defined"));
923 9006e9f8 Scott Ullrich
924 7c0571ce Seth Mos
	$iflist = get_configured_interface_list();
925
	foreach($iflist as $ifname) {
926
		if($config['interfaces'][$ifname]['if'] == $gifif) {
927 e2b6e604 Seth Mos
			if(get_interface_gateway($ifname)) {
928
				system_routing_configure($ifname);
929
				break;
930
			}
931 7c0571ce Seth Mos
			if(get_interface_gateway_v6($ifname)) {
932
				system_routing_configure($ifname);
933
				break;
934
			}
935
		}
936
	}
937 283e9180 Seth Mos
938 a687f866 Namezero
939 283e9180 Seth Mos
	if(is_ipaddrv4($gif['tunnel-remote-addr']))
940
		file_put_contents("{$g['tmp_path']}/{$gifif}_router", $gif['tunnel-remote-addr']);
941
	if(is_ipaddrv6($gif['tunnel-remote-addr']))
942
		file_put_contents("{$g['tmp_path']}/{$gifif}_routerv6", $gif['tunnel-remote-addr']);
943 582d2452 Ermal Luçi
944 1c3ddd9e Renato Botelho
	if (is_ipaddrv4($realifgw)) {
945
		mwexec("route change -host {$gif['remote-addr']} {$realifgw}");
946
	}
947
	if (is_ipaddrv6($realifgw)) {
948
		mwexec("route change -host -inet6 {$gif['remote-addr']} {$realifgw}");
949
	}
950 01a58d89 smos
951 9006e9f8 Scott Ullrich
	return $gifif;
952 582d2452 Ermal Luçi
}
953
954 eba938e3 Scott Ullrich
function interfaces_configure() {
955 9b1c39e3 Ermal Luçi
	global $config, $g;
956
957 7734aea6 Andrew Thompson
	if ($g['platform'] == 'jail')
958
		return;
959
960 a5d6f60b Ermal Lu?i
	/* Set up our loopback interface */
961 4aca19b3 Scott Ullrich
	interfaces_loopback_configure();
962 a5d6f60b Ermal Lu?i
963 f3bddb47 Ermal
	/* create the unconfigured wireless clones */
964
	interfaces_create_wireless_clones();
965
966 541b7c56 Scott Ullrich
	/* set up LAGG virtual interfaces */
967
	interfaces_lagg_configure();
968
969 acc1e9d0 Scott Ullrich
	/* set up VLAN virtual interfaces */
970
	interfaces_vlan_configure();
971
972 5f1e1d26 Ermal Lu?i
	interfaces_qinq_configure();
973
974 67ee1ec5 Ermal Luçi
	$iflist = get_configured_interface_with_descr();
975 9b1c39e3 Ermal Luçi
	$delayed_list = array();
976
	$bridge_list = array();
977 ef1c048b Ermal
	$track6_list = array();
978 be45aa79 Renato Botelho
979 871768cf Ermal
	/* This is needed to speedup interfaces on bootup. */
980
	$reload = false;
981 ae17d2e9 Ermal
	if (!$g['booting'])
982 871768cf Ermal
		$reload = true;
983
984 67ee1ec5 Ermal Luçi
	foreach($iflist as $if => $ifname) {
985 0dc702f3 Ermal Lu?i
		$realif = $config['interfaces'][$if]['if'];
986 be45aa79 Renato Botelho
		if (strstr($realif, "bridge"))
987 9b1c39e3 Ermal Luçi
			$bridge_list[$if] = $ifname;
988
		else if (strstr($realif, "gre"))
989
			$delayed_list[$if] = $ifname;
990
		else if (strstr($realif, "gif"))
991
			$delayed_list[$if] = $ifname;
992 d09d53ac Ermal
		else if (strstr($realif, "ovpn")) {
993
			//echo "Delaying OpenVPN interface configuration...done.\n";
994
			continue;
995 a823022d Ermal
		} else if (!empty($config['interfaces'][$if]['ipaddrv6']) && $config['interfaces'][$if]['ipaddrv6'] == "track6") {
996 3d92cd88 Renato Botelho
			$track6_list[$if] = $ifname;
997 d09d53ac Ermal
		} else {
998 9b1c39e3 Ermal Luçi
			if ($g['booting'])
999 07e40c1f Carlos Eduardo Ramos
				printf(gettext("Configuring %s interface..."), $ifname);
1000 a687f866 Namezero
1001 9006e9f8 Scott Ullrich
			if($g['debug'])
1002 07e40c1f Carlos Eduardo Ramos
				log_error(sprintf(gettext("Configuring %s"), $ifname));
1003 871768cf Ermal
			interface_configure($if, $reload);
1004 be45aa79 Renato Botelho
			if ($g['booting'])
1005 07e40c1f Carlos Eduardo Ramos
				echo gettext( "done.") . "\n";
1006 9b1c39e3 Ermal Luçi
		}
1007
	}
1008
1009 d7f1891b Ermal
	/*
1010
	 * NOTE: The following function parameter consists of
1011
	 *	1 - Do not load gre/gif/bridge with parent/member as vip
1012
	 *	2 - Do load gre/gif/bridge with parent/member as vip
1013
	 */
1014
1015 d7147b1c Scott Ullrich
	/* set up GRE virtual interfaces */
1016 d7f1891b Ermal
	interfaces_gre_configure(1);
1017 9b1c39e3 Ermal Luçi
1018 d7147b1c Scott Ullrich
	/* set up GIF virtual interfaces */
1019 d7f1891b Ermal
	interfaces_gif_configure(1);
1020
1021
	/* set up BRIDGe virtual interfaces */
1022
	interfaces_bridge_configure(1);
1023
1024 ef1c048b Ermal
	foreach ($track6_list as $if => $ifname) {
1025
		if ($g['booting'])
1026
			printf(gettext("Configuring %s interface..."), $ifname);
1027
		if ($g['debug'])
1028
			log_error(sprintf(gettext("Configuring %s"), $ifname));
1029
1030
		interface_configure($if, $reload);
1031
1032
		if ($g['booting'])
1033
			echo gettext("done.") . "\n";
1034
	}
1035
1036 d7f1891b Ermal
	/* bring up vip interfaces */
1037
	interfaces_vips_configure();
1038
1039
	/* set up GRE virtual interfaces */
1040
	interfaces_gre_configure(2);
1041
1042
	/* set up GIF virtual interfaces */
1043
	interfaces_gif_configure(2);
1044
1045 9b1c39e3 Ermal Luçi
	foreach ($delayed_list as $if => $ifname) {
1046
		if ($g['booting'])
1047 07e40c1f Carlos Eduardo Ramos
			printf(gettext("Configuring %s interface..."), $ifname);
1048 1c3ddd9e Renato Botelho
		if ($g['debug'])
1049
			log_error(sprintf(gettext("Configuring %s"), $ifname));
1050 67ee1ec5 Ermal Luçi
1051 871768cf Ermal
		interface_configure($if, $reload);
1052 4476d447 Ermal Luçi
1053 9b1c39e3 Ermal Luçi
		if ($g['booting'])
1054 07e40c1f Carlos Eduardo Ramos
			echo gettext("done.") . "\n";
1055 67ee1ec5 Ermal Luçi
	}
1056 cfc707f7 Scott Ullrich
1057 d7147b1c Scott Ullrich
	/* set up BRIDGe virtual interfaces */
1058 d7f1891b Ermal
	interfaces_bridge_configure(2);
1059 9b1c39e3 Ermal Luçi
1060 d7147b1c Scott Ullrich
	foreach ($bridge_list as $if => $ifname) {
1061
		if ($g['booting'])
1062 07e40c1f Carlos Eduardo Ramos
			printf(gettext("Configuring %s interface..."), $ifname);
1063 d7147b1c Scott Ullrich
		if($g['debug'])
1064 07e40c1f Carlos Eduardo Ramos
			log_error(sprintf(gettext("Configuring %s"), $ifname));
1065 9b1c39e3 Ermal Luçi
1066 871768cf Ermal
		interface_configure($if, $reload);
1067 9b1c39e3 Ermal Luçi
1068 d7147b1c Scott Ullrich
		if ($g['booting'])
1069 07e40c1f Carlos Eduardo Ramos
			echo gettext("done.") . "\n";
1070 d7147b1c Scott Ullrich
	}
1071 9b1c39e3 Ermal Luçi
1072 42753d25 Ermal Lu?i
	/* configure interface groups */
1073
	interfaces_group_setup();
1074
1075 5b237745 Scott Ullrich
	if (!$g['booting']) {
1076
		/* reconfigure static routes (kernel may have deleted them) */
1077
		system_routing_configure();
1078 cfc707f7 Scott Ullrich
1079 5b237745 Scott Ullrich
		/* reload IPsec tunnels */
1080
		vpn_ipsec_configure();
1081 cfc707f7 Scott Ullrich
1082 f620d00d Ermal Luçi
		/* reload dhcpd (interface enabled/disabled status may have changed) */
1083 5b237745 Scott Ullrich
		services_dhcpd_configure();
1084 cfc707f7 Scott Ullrich
1085 5b237745 Scott Ullrich
		/* restart dnsmasq */
1086
		services_dnsmasq_configure();
1087 4d18de6a Scott Ullrich
1088 c597d50f Scott Ullrich
		/* reload captive portal */
1089 491652bf Ermal
		if (function_exists('captiveportal_init_rules'))
1090
			captiveportal_init_rules();
1091 5b237745 Scott Ullrich
	}
1092 cfc707f7 Scott Ullrich
1093 5b237745 Scott Ullrich
	return 0;
1094
}
1095
1096 7a18dfa4 lgcosta
function interface_reconfigure($interface = "wan", $reloadall = false) {
1097 80bf3f4a Ermal Luçi
	interface_bring_down($interface);
1098 7a18dfa4 lgcosta
	interface_configure($interface, $reloadall);
1099 80bf3f4a Ermal Luçi
}
1100
1101 91a38e1f Ermal
function interface_vip_bring_down($vip) {
1102 962fd685 Ermal
	global $g;
1103
1104 abcb2bed Ermal Lu?i
	switch ($vip['mode']) {
1105
	case "proxyarp":
1106 962fd685 Ermal
		$vipif = get_real_interface($vip['interface']);
1107 ca942829 Ermal
		if (file_exists("{$g['varrun_path']}/choparp_{$vipif}.pid"))
1108
			killbypid("{$g['varrun_path']}/choparp_{$vipif}.pid");
1109 abcb2bed Ermal Lu?i
		break;
1110
	case "ipalias":
1111 435f11c8 Ermal Lu?i
		$vipif = get_real_interface($vip['interface']);
1112 5918f9b7 Ermal
		if (does_interface_exist($vipif)) {
1113
			if (is_ipaddrv6($vip['subnet']))
1114
				mwexec("/sbin/ifconfig {$vipif} inet6 {$vip['subnet']} -alias");
1115
			else
1116
				pfSense_interface_deladdress($vipif, $vip['subnet']);
1117
		}
1118 abcb2bed Ermal Lu?i
		break;
1119
	case "carp":
1120 7b47bd4c Ermal
		$vipif = "{$vip['interface']}_vip{$vip['vhid']}";
1121 be45aa79 Renato Botelho
		if (does_interface_exist($vipif))
1122 871768cf Ermal
			pfSense_interface_destroy($vipif);
1123 abcb2bed Ermal Lu?i
		break;
1124
	}
1125
}
1126
1127 9343d750 Ermal
function interface_bring_down($interface = "wan", $destroy = false, $ifacecfg = false) {
1128 80bf3f4a Ermal Luçi
	global $config, $g;
1129
1130 99c2a28b Ermal Luçi
	if (!isset($config['interfaces'][$interface]))
1131 be45aa79 Renato Botelho
		return;
1132 203e4bb6 Ermal
1133
	if ($g['debug'])
1134
		log_error("Calling interface down for interface {$interface}, destroy is " . (($destroy) ? 'true' : 'false'));
1135 37fb708c smos
1136 e12ad49f Renato Botelho
	if ($ifacecfg === false) {
1137 9343d750 Ermal
		$ifcfg = $config['interfaces'][$interface];
1138 e12ad49f Renato Botelho
		$ppps = $config['ppps']['ppp'];
1139
		$realif = get_real_interface($interface);
1140
	} elseif (!is_array($ifacecfg)) {
1141 9343d750 Ermal
		log_error(gettext("Wrong parameters used during interface_bring_down"));
1142 e12ad49f Renato Botelho
	} else {
1143
		$ifcfg = $ifacecfg['ifcfg'];
1144
		$ppps = $ifacecfg['ppps'];
1145
		if (isset($ifacecfg['ifcfg']['realif']))
1146
			$realif = $ifacecfg['ifcfg']['realif'];
1147
		else
1148
			$realif = get_real_interface($interface);
1149
	}
1150 80bf3f4a Ermal Luçi
1151
	switch ($ifcfg['ipaddr']) {
1152 0810c115 gnhb
	case "ppp":
1153 80bf3f4a Ermal Luçi
	case "pppoe":
1154
	case "pptp":
1155 39f750b5 gnhb
	case "l2tp":
1156 e12ad49f Renato Botelho
		if (is_array($ppps) && count($ppps)) {
1157
			foreach ($ppps as $pppid => $ppp) {
1158 a138f4fb Ermal
				if ($realif == $ppp['if']) {
1159 c8d23069 gnhb
					if (isset($ppp['ondemand']) && !$destroy){
1160
						send_event("interface reconfigure {$interface}");
1161
						break;
1162
					}
1163 a8d6ac1a Ermal
					if (file_exists("{$g['varrun_path']}/{$ppp['type']}_{$interface}.pid")) {
1164
						killbypid("{$g['varrun_path']}/{$ppp['type']}_{$interface}.pid");
1165 c8d23069 gnhb
						sleep(2);
1166 8d9cbe6f Ermal
					}
1167 64e6490a Ermal
					unlink_if_exists("{$g['varetc_path']}/mpd_{$interface}.conf");
1168 a138f4fb Ermal
					break;
1169
				}
1170
			}
1171
		}
1172 80bf3f4a Ermal Luçi
		break;
1173
	case "dhcp":
1174 5d478ecc Ermal Lu?i
		$pid = find_dhclient_process($realif);
1175 f07bee94 Scott Ullrich
		if($pid)
1176 deb39cf2 Ermal
			posix_kill($pid, SIGTERM);
1177 37fb708c smos
		sleep(1);
1178
		unlink_if_exists("{$g['varetc_path']}/dhclient_{$interface}.conf");
1179
		if(does_interface_exist("$realif")) {
1180
			mwexec("/sbin/ifconfig " . escapeshellarg($realif) . " delete", true);
1181
			if ($destroy == true)
1182
				pfSense_interface_flags($realif, -IFF_UP);
1183
			mwexec("/usr/sbin/arp -d -i {$realif} -a");
1184
		}
1185
		break;
1186
	default:
1187
		if(does_interface_exist("$realif")) {
1188
			mwexec("/sbin/ifconfig " . escapeshellarg($realif) . " delete", true);
1189
			if ($destroy == true)
1190
				pfSense_interface_flags($realif, -IFF_UP);
1191
			mwexec("/usr/sbin/arp -d -i {$realif} -a");
1192
		}
1193
		break;
1194
	}
1195
1196
	switch ($ifcfg['ipaddrv6']) {
1197 feb88a14 smos
	case "slaac":
1198 37fb708c smos
	case "dhcp6":
1199 c65d3051 Seth Mos
		$pidv6 = find_dhcp6c_process($realif);
1200 1af4f4e0 Ermal
		if($pidv6)
1201
			posix_kill($pidv6, SIGTERM);
1202 10e000f7 jim-p
		$pidv6 = find_rtsold_process($realif);
1203 c495f88b Seth Mos
		if($pidv6)
1204 82b50e76 Ermal
			posix_kill($pidv6, SIGTERM);
1205 74fa57aa smos
		sleep(3);
1206 c495f88b Seth Mos
		unlink_if_exists("{$g['varetc_path']}/dhcp6c_{$interface}.conf");
1207 e017a46a Ermal
		if (does_interface_exist("$realif")) {
1208 66c73aab Ermal
			$ip6 = get_interface_ipv6($interface);
1209
			if (is_ipaddrv6($ip6))
1210
				mwexec("/sbin/ifconfig " . escapeshellarg($realif) . " inet6 {$ip6} delete", true);
1211 e49a2031 Ermal
			if ($destroy == true)
1212
				pfSense_interface_flags($realif, -IFF_UP);
1213 5630c91c Ermal Lu?i
			mwexec("/usr/sbin/arp -d -i {$realif} -a");
1214 f07bee94 Scott Ullrich
		}
1215 80bf3f4a Ermal Luçi
		break;
1216 3f383504 smos
	case "6rd":
1217 31c43fd3 smos
	case "6to4":
1218 7d1f2eac Ermal
		$realif = "{$interface}_stf";
1219 31c43fd3 smos
		if(does_interface_exist("$realif")) {
1220 66c73aab Ermal
			$ip6 = get_interface_ipv6($interface);
1221
			if (is_ipaddrv6($ip6))
1222
				mwexec("/sbin/ifconfig " . escapeshellarg($realif) . " inet6 {$ip6} delete", true);
1223 31c43fd3 smos
			if ($destroy == true)
1224
				pfSense_interface_flags($realif, -IFF_UP);
1225 be45aa79 Renato Botelho
		}
1226 31c43fd3 smos
		break;
1227 80bf3f4a Ermal Luçi
	default:
1228 f07bee94 Scott Ullrich
		if(does_interface_exist("$realif")) {
1229 66c73aab Ermal
			$ip6 = get_interface_ipv6($interface);
1230
			if (is_ipaddrv6($ip6))
1231
				mwexec("/sbin/ifconfig " . escapeshellarg($realif) . " inet6 {$ip6} delete", true);
1232 80fae0e2 Ermal Lu?i
			if (!empty($ifcfg['ipaddrv6']) && is_ipaddrv6($ifcfg['ipaddrv6']))
1233
				mwexec("/sbin/ifconfig " . escapeshellarg($realif) . " inet6 {$ifcfg['ipaddrv6']} delete", true);
1234 e49a2031 Ermal
			if ($destroy == true)
1235
				pfSense_interface_flags($realif, -IFF_UP);
1236 5630c91c Ermal Lu?i
			mwexec("/usr/sbin/arp -d -i {$realif} -a");
1237 f07bee94 Scott Ullrich
		}
1238 80bf3f4a Ermal Luçi
		break;
1239
	}
1240 eb772abd Scott Ullrich
1241 97f7a517 jim-p
	if (file_exists("{$g['tmp_path']}/{$realif}_router"))
1242
		$old_router = trim(file_get_contents("{$g['tmp_path']}/{$realif}_router"));
1243 96f7a687 jim-p
//	log_error("Checking for old router states: {$g['tmp_path']}/{$realif}_router = {$old_router}");
1244
	if (!empty($old_router)) {
1245
		log_error("Clearing states to old gateway {$old_router}.");
1246 1befdbf8 Ermal
		mwexec("/sbin/pfctl -i {$realif} -Fs -G {$old_router}");
1247 96f7a687 jim-p
	}
1248 37fb708c smos
1249 73ee49f2 gnhb
	/* remove interface up file if it exists */
1250
	unlink_if_exists("{$g['tmp_path']}/{$realif}up");
1251
	unlink_if_exists("{$g['vardb_path']}/{$interface}ip");
1252 c495f88b Seth Mos
	unlink_if_exists("{$g['vardb_path']}/{$interface}ipv6");
1253 73ee49f2 gnhb
	unlink_if_exists("{$g['tmp_path']}/{$realif}_router");
1254 c495f88b Seth Mos
	unlink_if_exists("{$g['tmp_path']}/{$realif}_routerv6");
1255 86dcdfc9 Ermal
	unlink_if_exists("{$g['varetc_path']}/nameserver_{$realif}");
1256
	unlink_if_exists("{$g['varetc_path']}/searchdomain_{$realif}");
1257 be45aa79 Renato Botelho
1258 b5582f49 Erik Fonnesbeck
	/* hostapd and wpa_supplicant do not need to be running when the interface is down.
1259
	 * They will also use 100% CPU if running after the wireless clone gets deleted. */
1260
	if (is_array($ifcfg['wireless'])) {
1261 97f3ce0f Phil Davis
		kill_hostapd($realif);
1262 b5582f49 Erik Fonnesbeck
		mwexec(kill_wpasupplicant($realif));
1263
	}
1264
1265 97973ed8 Ermal Luçi
	if ($destroy == true) {
1266 1e8a05a2 bcyrill
		if (preg_match("/^[a-z0-9]+_vip|^tun|^ovpn|^gif|^gre|^lagg|^bridge|vlan|_stf$/i", $realif))
1267 871768cf Ermal
			pfSense_interface_destroy($realif);
1268 be45aa79 Renato Botelho
	}
1269 9006e9f8 Scott Ullrich
1270 80bf3f4a Ermal Luçi
	return;
1271 5b237745 Scott Ullrich
}
1272
1273 e5d558bf gnhb
function interfaces_ptpid_used($ptpid) {
1274
	global $config;
1275
1276
	if (is_array($config['ppps']['ppp']))
1277
		foreach ($config['ppps']['ppp'] as & $settings)
1278
			if ($ptpid == $settings['ptpid'])
1279
				return true;
1280
1281
	return false;
1282
}
1283
1284
function interfaces_ptpid_next() {
1285
1286
	$ptpid = 0;
1287
	while(interfaces_ptpid_used($ptpid))
1288
		$ptpid++;
1289
1290
	return $ptpid;
1291
}
1292
1293 70e46e62 Ermal
function getMPDCRONSettings($pppif) {
1294 e5d558bf gnhb
	global $config;
1295 70e46e62 Ermal
1296
	$cron_cmd_file = "{$g['varetc_path']}/pppoe_restart_{$pppif}";
1297 e5d558bf gnhb
	if (is_array($config['cron']['item'])) {
1298 70e46e62 Ermal
		foreach ($config['cron']['item'] as $i => $item) {
1299
			if (stripos($item['command'], $cron_cmd_file) !== false)
1300 e5d558bf gnhb
				return array("ID" => $i, "ITEM" => $item);
1301
		}
1302
	}
1303 70e46e62 Ermal
1304 e5d558bf gnhb
	return NULL;
1305
}
1306
1307
function handle_pppoe_reset($post_array) {
1308
	global $config, $g;
1309
1310 70e46e62 Ermal
	$pppif = "{$post_array['type']}{$post_array['ptpid']}";
1311
	$cron_cmd_file = "{$g['varetc_path']}/pppoe_restart_{$pppif}";
1312 5c8e8a17 gnhb
1313 be45aa79 Renato Botelho
	if (!is_array($config['cron']['item']))
1314
		$config['cron']['item'] = array();
1315 70e46e62 Ermal
1316 1d7e1d6c gnhb
	$itemhash = getMPDCRONSettings($pppif);
1317 be45aa79 Renato Botelho
1318 e5d558bf gnhb
	// reset cron items if necessary and return
1319
	if (empty($post_array['pppoe-reset-type'])) {
1320 70e46e62 Ermal
		if (isset($itemhash))
1321 e5d558bf gnhb
			unset($config['cron']['item'][$itemhash['ID']]);
1322
		sigkillbypid("{$g['varrun_path']}/cron.pid", "HUP");
1323
		return;
1324
	}
1325
1326 be45aa79 Renato Botelho
	if (empty($itemhash))
1327 70e46e62 Ermal
		$itemhash = array();
1328
	$item = array();
1329 e5d558bf gnhb
	if (isset($post_array['pppoe-reset-type']) && $post_array['pppoe-reset-type'] == "custom") {
1330
		$item['minute'] = $post_array['pppoe_resetminute'];
1331
		$item['hour'] = $post_array['pppoe_resethour'];
1332
		if (isset($post_array['pppoe_resetdate']) && $post_array['pppoe_resetdate'] <> "") {
1333
			$date = explode("/", $post_array['pppoe_resetdate']);
1334
			$item['mday'] = $date[1];
1335
			$item['month'] = $date[0];
1336
		} else {
1337
			$item['mday'] = "*";
1338
			$item['month'] = "*";
1339
		}
1340
		$item['wday'] = "*";
1341
		$item['who'] = "root";
1342 70e46e62 Ermal
		$item['command'] = $cron_cmd_file;
1343 e5d558bf gnhb
	} else if (isset($post_array['pppoe-reset-type']) && $post_array['pppoe-reset-type'] == "preset") {
1344
		switch ($post_array['pppoe_pr_preset_val']) {
1345 70e46e62 Ermal
		case "monthly":
1346
			$item['minute'] = "0";
1347
			$item['hour'] = "0";
1348
			$item['mday'] = "1";
1349
			$item['month'] = "*";
1350
			$item['wday'] = "*";
1351
			break;
1352 e5d558bf gnhb
	        case "weekly":
1353 70e46e62 Ermal
			$item['minute'] = "0";
1354
			$item['hour'] = "0";
1355
			$item['mday'] = "*";
1356
			$item['month'] = "*";
1357
			$item['wday'] = "0";
1358
			break;
1359
		case "daily":
1360
			$item['minute'] = "0";
1361
			$item['hour'] = "0";
1362
			$item['mday'] = "*";
1363
			$item['month'] = "*";
1364
			$item['wday'] = "*";
1365
			break;
1366
		case "hourly":
1367
			$item['minute'] = "0";
1368
			$item['hour'] = "*";
1369
			$item['mday'] = "*";
1370
			$item['month'] = "*";
1371
			$item['wday'] = "*";
1372
			break;
1373 e5d558bf gnhb
		} // end switch
1374 70e46e62 Ermal
		$item['who'] = "root";
1375
		$item['command'] = $cron_cmd_file;
1376
	}
1377
	if (empty($item))
1378
		return;
1379 be45aa79 Renato Botelho
	if (isset($item['ID']))
1380 70e46e62 Ermal
		$config['cron']['item'][$item['ID']] = $item;
1381 be45aa79 Renato Botelho
	else
1382 e5d558bf gnhb
		$config['cron']['item'][] = $item;
1383
}
1384
1385 70e46e62 Ermal
/*
1386
 * This function can configure PPPoE, MLPPP (PPPoE), PPTP.
1387
 * It writes the mpd config file to /var/etc every time the link is opened.
1388
 */
1389 cb37d8fa gnhb
function interface_ppps_configure($interface) {
1390
	global $config, $g;
1391 01c201e3 Ermal
1392
	/* Return for unassigned interfaces. This is a minimum requirement. */
1393
	if (empty($config['interfaces'][$interface]))
1394
		return 0;
1395
	$ifcfg = $config['interfaces'][$interface];
1396
	if (!isset($ifcfg['enable']))
1397
		return 0;
1398
1399 3a906378 gnhb
	// mpd5 requires a /var/spool/lock directory for PPP modem links.
1400
	if(!is_dir("/var/spool/lock")) {
1401
		exec("/bin/mkdir -p /var/spool/lock");
1402
		exec("/bin/chmod a+rw /var/spool/lock/.");
1403
	}
1404 7e631290 smos
	// mpd5 modem chat script expected in the same directory as the mpd_xxx.conf files
1405 3a906378 gnhb
	if (!file_exists("{$g['varetc_path']}/mpd.script"))
1406
		mwexec("/bin/ln -s /usr/local/sbin/mpd.script {$g['varetc_path']}/.");
1407 01c201e3 Ermal
1408 cb37d8fa gnhb
	if (is_array($config['ppps']['ppp']) && count($config['ppps']['ppp'])) {
1409
		foreach ($config['ppps']['ppp'] as $pppid => $ppp) {
1410 f7480829 gnhb
			if ($ifcfg['if'] == $ppp['if'])
1411 cb37d8fa gnhb
				break;
1412
		}
1413
	}
1414 f7480829 gnhb
	if (!$ppp || $ifcfg['if'] != $ppp['if']){
1415 07e40c1f Carlos Eduardo Ramos
		log_error(sprintf(gettext("Can't find PPP config for %s in interface_ppps_configure()."), $ifcfg['if']));
1416 3a906378 gnhb
		return 0;
1417 cb37d8fa gnhb
	}
1418 3a906378 gnhb
	$pppif = $ifcfg['if'];
1419 cb37d8fa gnhb
	if ($ppp['type'] == "ppp")
1420
		$type = "modem";
1421
	else
1422
		$type = $ppp['type'];
1423 be45aa79 Renato Botelho
	$upper_type = strtoupper($ppp['type']);
1424 01c201e3 Ermal
1425 3a906378 gnhb
	if($g['booting']) {
1426 bfbb9bc0 Ermal
		$descr = isset($ifcfg['descr']) ? $ifcfg['descr'] : strtoupper($interface);
1427 3a90c973 gnhb
		echo "starting {$pppif} link...";
1428 3a906378 gnhb
		// Do not re-configure the interface if we are booting and it's already been started
1429
		if(file_exists("{$g['varrun_path']}/{$ppp['type']}_{$interface}.pid"))
1430
			return 0;
1431
	}
1432 01c201e3 Ermal
1433 3a906378 gnhb
	$ports = explode(',',$ppp['ports']);
1434 bfbb9bc0 Ermal
	if ($type != "modem") {
1435 8e9d1265 Renato Botelho
		foreach ($ports as $pid => $port) {
1436 bfbb9bc0 Ermal
			$ports[$pid] = get_real_interface($port);
1437 8e9d1265 Renato Botelho
			if (empty($ports[$pid]))
1438
				return 0;
1439
		}
1440 bfbb9bc0 Ermal
	}
1441 3a906378 gnhb
	$localips = explode(',',$ppp['localip']);
1442
	$gateways = explode(',',$ppp['gateway']);
1443
	$subnets = explode(',',$ppp['subnet']);
1444 01c201e3 Ermal
1445 3a906378 gnhb
	/* We bring up the parent interface first because if DHCP is configured on the parent we need
1446 01c201e3 Ermal
	 * to obtain an address first so we can write it in the mpd .conf file for PPTP and L2TP configs
1447
	 */
1448 3a906378 gnhb
	foreach($ports as $pid => $port){
1449 23721285 gnhb
		switch ($ppp['type']) {
1450 be45aa79 Renato Botelho
			case "pppoe":
1451 3a906378 gnhb
				/* Bring the parent interface up */
1452
				interfaces_bring_up($port);
1453 3d04de61 Ermal
				pfSense_ngctl_attach(".", $port);
1454 84086442 Renato Botelho
				/* Enable setautosrc to automatically change mac address if parent interface's changes */
1455
				mwexec("ngctl msg {$port}: setautosrc 1");
1456 3a906378 gnhb
				break;
1457
			case "pptp":
1458
			case "l2tp":
1459
				/* configure interface */
1460 69c1b043 gnhb
				if(is_ipaddr($localips[$pid])){
1461 3a906378 gnhb
					// Manually configure interface IP/subnet
1462 bfbb9bc0 Ermal
					pfSense_interface_setaddress($port, "{$localips[$pid]}/{$subnets[$pid]}");
1463
					interfaces_bring_up($port);
1464 69c1b043 gnhb
				} else if (empty($localips[$pid]))
1465
					$localips[$pid] = get_interface_ip($port); // try to get the interface IP from the port
1466 be45aa79 Renato Botelho
1467 69c1b043 gnhb
				if(!is_ipaddr($localips[$pid])){
1468 d421e319 Ermal
					log_error("Could not get a Local IP address for PPTP/L2TP link on {$port} in interfaces_ppps_configure. Using 0.0.0.0 ip!");
1469
					$localips[$pid] = "0.0.0.0";
1470 3a906378 gnhb
				}
1471 69c1b043 gnhb
				if(!is_ipaddr($gateways[$pid])){
1472 addc0439 Renato Botelho
					log_error(sprintf(gettext('Could not get a PPTP/L2TP Remote IP address from %1$s for %2$s in interfaces_ppps_configure.'), $dhcp_gateway, $gway));
1473 69c1b043 gnhb
					return 0;
1474 3a906378 gnhb
				}
1475 3d04de61 Ermal
				pfSense_ngctl_attach(".", $port);
1476 3a906378 gnhb
				break;
1477
			case "ppp":
1478
				if (!file_exists("{$port}")) {
1479 07e40c1f Carlos Eduardo Ramos
					log_error(sprintf(gettext("Device %s does not exist. PPP link cannot start without the modem device."), $port));
1480 23721285 gnhb
					return 0;
1481 3a906378 gnhb
				}
1482
				break;
1483
			default:
1484 07e40c1f Carlos Eduardo Ramos
				log_error(sprintf(gettext("Unkown %s configured as ppp interface."), $type));
1485 3a906378 gnhb
				break;
1486
		}
1487
	}
1488 be45aa79 Renato Botelho
1489 cb37d8fa gnhb
	if (is_array($ports) && count($ports) > 1)
1490
		$multilink = "enable";
1491
	else
1492
		$multilink = "disable";
1493 be45aa79 Renato Botelho
1494 cb37d8fa gnhb
	if ($type == "modem"){
1495
		if (is_ipaddr($ppp['localip']))
1496
			$localip = $ppp['localip'];
1497
		else
1498
			$localip = '0.0.0.0';
1499
1500
		if (is_ipaddr($ppp['gateway']))
1501
			$gateway = $ppp['gateway'];
1502
		else
1503 23721285 gnhb
			$gateway = "10.64.64.{$pppid}";
1504 cb37d8fa gnhb
		$ranges = "{$localip}/0 {$gateway}/0";
1505 be45aa79 Renato Botelho
1506
		if (empty($ppp['apnum']))
1507 3a906378 gnhb
			$ppp['apnum'] = 1;
1508 23721285 gnhb
	} else
1509 cb37d8fa gnhb
		$ranges = "0.0.0.0/0 0.0.0.0/0";
1510 0661b194 gnhb
1511 be45aa79 Renato Botelho
	if (isset($ppp['ondemand']))
1512 cb37d8fa gnhb
		$ondemand = "enable";
1513
	else
1514
		$ondemand = "disable";
1515
	if (!isset($ppp['idletimeout']))
1516
		$ppp['idletimeout'] = 0;
1517 64d124c5 gnhb
1518 cb37d8fa gnhb
	if (empty($ppp['username']) && $type == "modem"){
1519
		$ppp['username'] = "user";
1520
		$ppp['password'] = "none";
1521
	}
1522
	if (empty($ppp['password']) && $type == "modem")
1523 00b702cc gnhb
		$passwd = "none";
1524
	else
1525
		$passwd = base64_decode($ppp['password']);
1526 0661b194 gnhb
1527
	$bandwidths = explode(',',$ppp['bandwidth']);
1528 6805d2d2 Ermal
	$defaultmtu = "1492";
1529
	if (!empty($ifcfg['mtu']))
1530
		$defaultmtu = intval($ifcfg['mtu']);
1531 0661b194 gnhb
	$mtus = explode(',',$ppp['mtu']);
1532
	$mrus = explode(',',$ppp['mru']);
1533
1534 c1cc447c gnhb
	if (isset($ppp['mrru']))
1535 0661b194 gnhb
		$mrrus = explode(',',$ppp['mrru']);
1536 c1cc447c gnhb
1537 cb37d8fa gnhb
	// Construct the mpd.conf file
1538
	$mpdconf = <<<EOD
1539
startup:
1540
	# configure the console
1541
	set console close
1542
	# configure the web server
1543
	set web close
1544
1545
default:
1546
{$ppp['type']}client:
1547
	create bundle static {$interface}
1548 07dfd121 Seth Mos
	set bundle enable ipv6cp
1549 cb37d8fa gnhb
	set iface name {$pppif}
1550
1551
EOD;
1552 0661b194 gnhb
	$setdefaultgw = false;
1553
	$founddefaultgw = false;
1554
	if (is_array($config['gateways']['gateway_item'])) {
1555
		foreach($config['gateways']['gateway_item'] as $gateway) {
1556
			if($interface == $gateway['interface'] && isset($gateway['defaultgw'])) {
1557
				$setdefaultgw = true;
1558
				break;
1559
			} else if (isset($gateway['defaultgw']) && !empty($gateway['interface'])) {
1560
				$founddefaultgw = true;
1561
				break;
1562
			}
1563
		}
1564
	}
1565 be45aa79 Renato Botelho
1566 82effddb gnhb
	if (($interface == "wan" && $founddefaultgw == false) || $setdefaultgw == true){
1567
		$setdefaultgw = true;
1568 cb37d8fa gnhb
		$mpdconf .= <<<EOD
1569
	set iface route default
1570
1571
EOD;
1572 82effddb gnhb
	}
1573 cb37d8fa gnhb
	$mpdconf .= <<<EOD
1574
	set iface {$ondemand} on-demand
1575
	set iface idle {$ppp['idletimeout']}
1576
1577
EOD;
1578
1579 0661b194 gnhb
	if (isset($ppp['ondemand']))
1580 cb37d8fa gnhb
		$mpdconf .= <<<EOD
1581 55f3ca1d gnhb
	set iface addrs 10.10.1.1 10.10.1.2
1582 cb37d8fa gnhb
1583
EOD;
1584 be45aa79 Renato Botelho
1585 0661b194 gnhb
	if (isset($ppp['tcpmssfix']))
1586 8adc1e49 gnhb
		$tcpmss = "disable";
1587
	else
1588
		$tcpmss = "enable";
1589 64d124c5 gnhb
		$mpdconf .= <<<EOD
1590 8adc1e49 gnhb
	set iface {$tcpmss} tcpmssfix
1591 64d124c5 gnhb
1592
EOD;
1593 0661b194 gnhb
1594 cb37d8fa gnhb
	$mpdconf .= <<<EOD
1595
	set iface up-script /usr/local/sbin/ppp-linkup
1596
	set iface down-script /usr/local/sbin/ppp-linkdown
1597
	set ipcp ranges {$ranges}
1598
1599
EOD;
1600 0661b194 gnhb
	if (isset($ppp['vjcomp']))
1601 cb37d8fa gnhb
		$mpdconf .= <<<EOD
1602 64d124c5 gnhb
	set ipcp no vjcomp
1603 cb37d8fa gnhb
1604
EOD;
1605
1606 bfbb9bc0 Ermal
	if (isset($config['system']['dnsallowoverride']))
1607 64d124c5 gnhb
		$mpdconf .= <<<EOD
1608
	set ipcp enable req-pri-dns
1609
	set ipcp enable req-sec-dns
1610
1611
EOD;
1612 23721285 gnhb
	if (!isset($ppp['verbose_log']))
1613
		$mpdconf .= <<<EOD
1614 5d9d443a gnhb
	#log -bund -ccp -chat -iface -ipcp -lcp -link
1615 0661b194 gnhb
1616 23721285 gnhb
EOD;
1617 64d124c5 gnhb
	foreach($ports as $pid => $port){
1618 bfbb9bc0 Ermal
		$port = get_real_interface($port);
1619 00b702cc gnhb
		$mpdconf .= <<<EOD
1620 cb37d8fa gnhb
1621 0661b194 gnhb
	create link static {$interface}_link{$pid} {$type}
1622 cb37d8fa gnhb
	set link action bundle {$interface}
1623
	set link {$multilink} multilink
1624
	set link keep-alive 10 60
1625
	set link max-redial 0
1626 64d124c5 gnhb
1627
EOD;
1628 0661b194 gnhb
		if (isset($ppp['shortseq']))
1629 00b702cc gnhb
			$mpdconf .= <<<EOD
1630 64d124c5 gnhb
	set link no shortseq
1631
1632
EOD;
1633 0661b194 gnhb
1634
		if (isset($ppp['acfcomp']))
1635 00b702cc gnhb
			$mpdconf .= <<<EOD
1636 64d124c5 gnhb
	set link no acfcomp
1637
1638
EOD;
1639 0661b194 gnhb
1640
		if (isset($ppp['protocomp']))
1641 00b702cc gnhb
			$mpdconf .= <<<EOD
1642 64d124c5 gnhb
	set link no protocomp
1643
1644
EOD;
1645 0661b194 gnhb
1646 00b702cc gnhb
		$mpdconf .= <<<EOD
1647 cb37d8fa gnhb
	set link disable chap pap
1648
	set link accept chap pap eap
1649 64d124c5 gnhb
	set link disable incoming
1650 cb37d8fa gnhb
1651
EOD;
1652 00b702cc gnhb
1653
1654 0661b194 gnhb
		if (!empty($bandwidths[$pid]))
1655 00b702cc gnhb
			$mpdconf .= <<<EOD
1656
	set link bandwidth {$bandwidths[$pid]}
1657 cb37d8fa gnhb
1658
EOD;
1659 0661b194 gnhb
1660 8adc1e49 gnhb
		if (empty($mtus[$pid]))
1661 6805d2d2 Ermal
			$mtus[$pid] = $defaultmtu;
1662 00b702cc gnhb
			$mpdconf .= <<<EOD
1663
	set link mtu {$mtus[$pid]}
1664 cb37d8fa gnhb
1665
EOD;
1666 0661b194 gnhb
1667
		if (!empty($mrus[$pid]))
1668 00b702cc gnhb
			$mpdconf .= <<<EOD
1669
	set link mru {$mrus[$pid]}
1670
1671 6a30f701 gnhb
EOD;
1672
1673
		if (!empty($mrrus[$pid]))
1674
			$mpdconf .= <<<EOD
1675
	set link mrru {$mrrus[$pid]}
1676
1677 00b702cc gnhb
EOD;
1678 0661b194 gnhb
1679 00b702cc gnhb
		$mpdconf .= <<<EOD
1680 cb37d8fa gnhb
	set auth authname "{$ppp['username']}"
1681
	set auth password {$passwd}
1682
1683
EOD;
1684 00b702cc gnhb
		if ($type == "modem") {
1685
			$mpdconf .= <<<EOD
1686 cb37d8fa gnhb
	set modem device {$ppp['ports']}
1687
	set modem script DialPeer
1688 73472985 Ermal
	set modem idle-script Ringback
1689 cb37d8fa gnhb
	set modem watch -cd
1690
	set modem var \$DialPrefix "DT"
1691
	set modem var \$Telephone "{$ppp['phone']}"
1692
1693
EOD;
1694 00b702cc gnhb
		}
1695
		if (isset($ppp['connect-timeout']) && $type == "modem") {
1696
			$mpdconf .= <<<EOD
1697 cb37d8fa gnhb
	set modem var \$ConnectTimeout "{$ppp['connect-timeout']}"
1698
1699
EOD;
1700 00b702cc gnhb
		}
1701
		if (isset($ppp['initstr']) && $type == "modem") {
1702
			$initstr = base64_decode($ppp['initstr']);
1703
			$mpdconf .= <<<EOD
1704 cb37d8fa gnhb
	set modem var \$InitString "{$initstr}"
1705
1706
EOD;
1707 00b702cc gnhb
		}
1708
		if (isset($ppp['simpin']) && $type == "modem") {
1709 03f7925a jim-p
			if($ppp['pin-wait'] == "")
1710 2a210730 smos
				$ppp['pin-wait'] = 0;
1711 00b702cc gnhb
			$mpdconf .= <<<EOD
1712 cb37d8fa gnhb
	set modem var \$SimPin "{$ppp['simpin']}"
1713
	set modem var \$PinWait "{$ppp['pin-wait']}"
1714
1715
EOD;
1716 00b702cc gnhb
		}
1717
		if (isset($ppp['apn']) && $type == "modem") {
1718
			$mpdconf .= <<<EOD
1719 cb37d8fa gnhb
	set modem var \$APN "{$ppp['apn']}"
1720
	set modem var \$APNum "{$ppp['apnum']}"
1721
1722
EOD;
1723 00b702cc gnhb
		}
1724 233e2af1 jim-p
		if ($type == "pppoe") {
1725
			// Send a null service name if none is set.
1726
			$provider = isset($ppp['provider']) ? $ppp['provider'] : "";
1727 00b702cc gnhb
			$mpdconf .= <<<EOD
1728 233e2af1 jim-p
	set pppoe service "{$provider}"
1729 cb37d8fa gnhb
1730
EOD;
1731 00b702cc gnhb
		}
1732 0661b194 gnhb
		if ($type == "pppoe")
1733 00b702cc gnhb
			$mpdconf .= <<<EOD
1734 64d124c5 gnhb
	set pppoe iface {$port}
1735 cb37d8fa gnhb
1736
EOD;
1737 0661b194 gnhb
1738 39f750b5 gnhb
		if ($type == "pptp" || $type == "l2tp") {
1739 00b702cc gnhb
			$mpdconf .= <<<EOD
1740 18ec0f13 Ermal
	set {$type} self {$localips[$pid]}
1741
	set {$type} peer {$gateways[$pid]}
1742 cb37d8fa gnhb
1743
EOD;
1744 00b702cc gnhb
		}
1745 be45aa79 Renato Botelho
1746 04f357bc Ermal
		$mpdconf .= "\topen\n";
1747 cb37d8fa gnhb
	} //end foreach($port)
1748
1749 df309b37 gnhb
1750
	/* Generate mpd.conf. If mpd_[interface].conf exists in the conf path, then link to it instead of generating a fresh conf file. */
1751
	if (file_exists("{$g['conf_path']}/mpd_{$interface}.conf"))
1752
		mwexec("/bin/ln -s {$g['conf_path']}/mpd_{$interface}.conf {$g['varetc_path']}/.");
1753
	else {
1754
		$fd = fopen("{$g['varetc_path']}/mpd_{$interface}.conf", "w");
1755
		if (!$fd) {
1756 07e40c1f Carlos Eduardo Ramos
			log_error(sprintf(gettext("Error: cannot open mpd_%s.conf in interface_ppps_configure().%s"), $interface, "\n"));
1757 df309b37 gnhb
			return 0;
1758
		}
1759
		// Write out mpd_ppp.conf
1760
		fwrite($fd, $mpdconf);
1761
		fclose($fd);
1762 14d079b3 Ermal
		unset($mpdconf);
1763 df309b37 gnhb
	}
1764 cb37d8fa gnhb
1765
	// Create the uptime log if requested and if it doesn't exist already, or delete it if it is no longer requested.
1766
	if (isset($ppp['uptime'])) {
1767
		if (!file_exists("/conf/{$pppif}.log")) {
1768
			conf_mount_rw();
1769
			mwexec("echo /dev/null > /conf/{$pppif}.log");
1770
			conf_mount_ro();
1771
		}
1772
	} else {
1773
		if (file_exists("/conf/{$pppif}.log")) {
1774
			conf_mount_rw();
1775
			mwexec("rm -f /conf/{$pppif}.log");
1776
			conf_mount_ro();
1777
		}
1778
	}
1779 92a1c8e6 Ermal
1780 7e631290 smos
	/* clean up old lock files */
1781
	foreach($ports as $port) {
1782 17d656fc smos
		if(file_exists("{$g['var_path']}/spool/lock/LCK..{$port}"))
1783
			unlink("{$g['var_path']}/spool/lock/LCK..{$port}");
1784 7e631290 smos
	}
1785
1786 3a906378 gnhb
	/* fire up mpd */
1787
	mwexec("/usr/local/sbin/mpd5 -b -k -d {$g['varetc_path']} -f mpd_{$interface}.conf -p {$g['varrun_path']}/{$ppp['type']}_{$interface}.pid -s ppp {$ppp['type']}client");
1788
1789 be45aa79 Renato Botelho
	// Check for PPPoE periodic reset request
1790 bfbb9bc0 Ermal
	if ($type == "pppoe") {
1791 70e46e62 Ermal
		if (!empty($ppp['pppoe-reset-type']))
1792
			interface_setup_pppoe_reset_file($ppp['if'], $interface);
1793 766bd6d0 gnhb
		else
1794 70e46e62 Ermal
			interface_setup_pppoe_reset_file($ppp['if']);
1795 cb37d8fa gnhb
	}
1796 302d646e smos
	/* wait for upto 10 seconds for the interface to appear (ppp(oe)) */
1797
	$i = 0;
1798
	while($i < 10) {
1799
		exec("/sbin/ifconfig {$ppp['if']} 2>&1", $out, $ret);
1800
		if($ret == 0)
1801
			break;
1802
		sleep(1);
1803
		$i++;
1804
	}
1805 cb37d8fa gnhb
1806 117f8e6f smos
	/* we only support the 3gstats.php for huawei modems for now. Will add more later. */
1807
	/* We should be able to launch the right version for each modem */
1808
	/* We can also guess the mondev from the manufacturer */
1809
	exec("usbconfig | egrep -ie '(huawei)'", $usbmodemoutput);
1810
	mwexec("/bin/ps auxww|grep \"{$interface}\" |grep \"[3]gstats\" | awk '{print $2}' |xargs kill");
1811 284101d3 smos
	foreach($ports as $port) {
1812 7056e4ed smos
		if(preg_match("/huawei/i", implode("\n", $usbmodemoutput))) {
1813 117f8e6f smos
			$mondev  = substr(basename($port), 0, -1);
1814
			$devlist = glob("/dev/{$mondev}?");
1815
			$mondev = basename(end($devlist));
1816 284101d3 smos
		}
1817 7056e4ed smos
		if(preg_match("/zte/i", implode("\n", $usbmodemoutput))) {
1818 284101d3 smos
			$mondev  = substr(basename($port), 0, -1) . "1";
1819
		}
1820
		log_error("Starting 3gstats.php on device '{$mondev}' for interface '{$interface}'");
1821
		mwexec_bg("/usr/local/bin/3gstats.php {$mondev} {$interface}");
1822 5e589685 smos
	}
1823
1824 23721285 gnhb
	return 1;
1825 cb37d8fa gnhb
}
1826
1827 abcb2bed Ermal Lu?i
function interfaces_carp_setup() {
1828 87a2efd1 Ermal Luçi
	global $g, $config;
1829 abcb2bed Ermal Lu?i
1830 84b32407 Ermal
	if (isset($config['system']['developerspew'])) {
1831 b932ef16 Scott Ullrich
		$mt = microtime();
1832 abcb2bed Ermal Lu?i
		echo "interfaces_carp_setup() being called $mt\n";
1833 b932ef16 Scott Ullrich
	}
1834 abcb2bed Ermal Lu?i
1835 b932ef16 Scott Ullrich
	if ($g['booting']) {
1836 07e40c1f Carlos Eduardo Ramos
		echo gettext("Configuring CARP settings...");
1837 7d0f4544 Scott Ullrich
		mute_kernel_msgs();
1838 a5250ebc Scott Ullrich
	}
1839 abcb2bed Ermal Lu?i
1840 b932ef16 Scott Ullrich
	/* suck in configuration items */
1841 84b32407 Ermal
	if ($config['hasync']) {
1842 f97a5b04 Darren Embry
		$pfsyncenabled = $config['hasync']['pfsyncenabled'];
1843
		$balanacing = $config['hasync']['balancing'];
1844
		$pfsyncinterface = $config['hasync']['pfsyncinterface'];
1845
		$pfsyncpeerip = $config['hasync']['pfsyncpeerip'];
1846 b932ef16 Scott Ullrich
	} else {
1847
		unset($pfsyncinterface);
1848
		unset($balanacing);
1849
		unset($pfsyncenabled);
1850 6008210b Scott Ullrich
	}
1851 abcb2bed Ermal Lu?i
1852 84b32407 Ermal
	if ($balanacing) {
1853
		mwexec("/sbin/sysctl net.inet.carp.arpbalance=1", true);
1854
		mwexec("/sbin/sysctl net.inet.carp.preempt=0", true);
1855 abcb2bed Ermal Lu?i
	} else
1856 be45aa79 Renato Botelho
		mwexec("/sbin/sysctl net.inet.carp.preempt=1", true);
1857 abcb2bed Ermal Lu?i
1858 84b32407 Ermal
	mwexec("sbin/sysctl net.inet.carp.log=1", true);
1859 abcb2bed Ermal Lu?i
	if (!empty($pfsyncinterface))
1860
		$carp_sync_int = get_real_interface($pfsyncinterface);
1861 84b32407 Ermal
	else
1862
		unset($carp_sync_int);
1863 abcb2bed Ermal Lu?i
1864 b932ef16 Scott Ullrich
	/* setup pfsync interface */
1865 84b32407 Ermal
	if ($carp_sync_int and $pfsyncenabled) {
1866 abcb2bed Ermal Lu?i
		if (is_ipaddr($pfsyncpeerip))
1867 dc2e5552 Renato Botelho
			$syncpeer = "syncpeer {$pfsyncpeerip}";
1868 abcb2bed Ermal Lu?i
		else
1869 dc2e5552 Renato Botelho
			$syncpeer = "-syncpeer";
1870
1871
		mwexec("/sbin/ifconfig pfsync0 syncdev {$carp_sync_int} {$syncpeer} up", false);
1872 abcb2bed Ermal Lu?i
1873 84b32407 Ermal
		sleep(1);
1874 2eb9c02f Ermal
1875 84b32407 Ermal
		/* XXX: Handle an issue with pfsync(4) and carp(4). In a cluster carp will come up before pfsync(4) has updated and so will cause issues
1876
		 * for existing sessions.
1877
		 */
1878 b32329fc smos
		log_error("waiting for pfsync...");
1879 1be1a67a PiBa-NL
		$i = 0;
1880
		while (intval(trim(`/sbin/ifconfig pfsync0 | /usr/bin/grep 'syncok: 0' | /usr/bin/grep -v grep | /usr/bin/wc -l`)) == 0 && $i < 30) {
1881
			$i++;
1882
			sleep(1);
1883
		}
1884 b32329fc smos
		log_error("pfsync done in $i seconds.");
1885
		log_error("Configuring CARP settings finalize...");
1886 b32ea59d Renato Botelho
	} else {
1887 fb6a3e7a Renato Botelho
		mwexec("/sbin/ifconfig pfsync0 -syncdev -syncpeer down", false);
1888 6930e805 Ermal
	}
1889 abcb2bed Ermal Lu?i
1890
	if($config['virtualip']['vip'])
1891 be45aa79 Renato Botelho
		mwexec("/sbin/sysctl net.inet.carp.allow=1", true);
1892 abcb2bed Ermal Lu?i
	else
1893 be45aa79 Renato Botelho
		mwexec("/sbin/sysctl net.inet.carp.allow=0", true);
1894
1895 abcb2bed Ermal Lu?i
	if ($g['booting']) {
1896
		unmute_kernel_msgs();
1897 07e40c1f Carlos Eduardo Ramos
		echo gettext("done.") . "\n";
1898 abcb2bed Ermal Lu?i
	}
1899 67ee1ec5 Ermal Luçi
}
1900
1901 962fd685 Ermal
function interface_proxyarp_configure($interface = "") {
1902 9006e9f8 Scott Ullrich
	global $config, $g;
1903
	if(isset($config['system']['developerspew'])) {
1904
		$mt = microtime();
1905
		echo "interface_proxyarp_configure() being called $mt\n";
1906
	}
1907 67ee1ec5 Ermal Luçi
1908 9006e9f8 Scott Ullrich
	/* kill any running choparp */
1909 962fd685 Ermal
	if (empty($interface))
1910
		killbyname("choparp");
1911 7c73f504 Ermal
	else {
1912
		$vipif = get_real_interface($interface);
1913
		if (file_exists("{$g['varrun_path']}/choparp_{$vipif}.pid"))
1914
			killbypid("{$g['varrun_path']}/choparp_{$vipif}.pid");
1915
	}
1916 1b58b513 Scott Ullrich
1917 7c73f504 Ermal
	$paa = array();
1918
	if (!empty($config['virtualip']) && is_array($config['virtualip']['vip'])) {
1919 e5d43d93 Scott Ullrich
1920 9006e9f8 Scott Ullrich
		/* group by interface */
1921
		foreach ($config['virtualip']['vip'] as $vipent) {
1922
			if ($vipent['mode'] === "proxyarp") {
1923
				if ($vipent['interface'])
1924
					$proxyif = $vipent['interface'];
1925
				else
1926
					$proxyif = "wan";
1927 be45aa79 Renato Botelho
1928 7e96ca27 Ermal
				if (!empty($interface) && $interface != $proxyif)
1929
					continue;
1930 abcb2bed Ermal Lu?i
1931 7c73f504 Ermal
				if (!is_array($paa[$proxyif]))
1932 9006e9f8 Scott Ullrich
					$paa[$proxyif] = array();
1933 7b2d4769 Bill Marquette
1934 9006e9f8 Scott Ullrich
				$paa[$proxyif][] = $vipent;
1935
			}
1936 962fd685 Ermal
		}
1937 9006e9f8 Scott Ullrich
	}
1938 e5d43d93 Scott Ullrich
1939 962fd685 Ermal
	if (!empty($interface)) {
1940
		if (is_array($paa[$interface])) {
1941
			$paaifip = get_interface_ip($interface);
1942 1c3ddd9e Renato Botelho
			if (!is_ipaddr($paaifip))
1943
				return;
1944
			$args = get_real_interface($interface) . " auto";
1945
			foreach ($paa[$interface] as $paent) {
1946
				if (isset($paent['subnet']))
1947
					$args .= " " . escapeshellarg("{$paent['subnet']}/{$paent['subnet_bits']}");
1948
				else if (isset($paent['range']))
1949
					$args .= " " . escapeshellarg($paent['range']['from'] . "-" . $paent['range']['to']);
1950
			}
1951
			mwexec_bg("/usr/local/sbin/choparp " . $args);
1952 962fd685 Ermal
		}
1953 7c73f504 Ermal
	} else if (count($paa) > 0) {
1954
		foreach ($paa as $paif => $paents)  {
1955 9006e9f8 Scott Ullrich
			$paaifip = get_interface_ip($paif);
1956 f814d3a6 Ermal
			if (!is_ipaddr($paaifip))
1957 9006e9f8 Scott Ullrich
				continue;
1958
			$args = get_real_interface($paif) . " auto";
1959
			foreach ($paents as $paent) {
1960
				if (isset($paent['subnet']))
1961
					$args .= " " . escapeshellarg("{$paent['subnet']}/{$paent['subnet_bits']}");
1962
				else if (isset($paent['range']))
1963 962fd685 Ermal
					$args .= " " . escapeshellarg($paent['range']['from'] . "-" . $paent['range']['to']);
1964 9006e9f8 Scott Ullrich
			}
1965
			mwexec_bg("/usr/local/sbin/choparp " . $args);
1966
		}
1967
	}
1968 9f6b1429 Scott Ullrich
}
1969
1970 e5ac67ed Ermal Lu?i
function interfaces_vips_configure($interface = "") {
1971 87a2efd1 Ermal Luçi
	global $g, $config;
1972 a04de17f Chris Buechler
	if(isset($config['system']['developerspew'])) {
1973
		$mt = microtime();
1974 123f030c Chris Buechler
		echo "interfaces_vips_configure() being called $mt\n";
1975 a04de17f Chris Buechler
	}
1976 abcb2bed Ermal Lu?i
	$paa = array();
1977
	if(is_array($config['virtualip']['vip'])) {
1978
		$carp_setuped = false;
1979 e5ac67ed Ermal Lu?i
		$anyproxyarp = false;
1980 abcb2bed Ermal Lu?i
		foreach ($config['virtualip']['vip'] as $vip) {
1981
			switch ($vip['mode']) {
1982
			case "proxyarp":
1983 123f030c Chris Buechler
				/* nothing it is handled on interface_proxyarp_configure() */
1984 e5ac67ed Ermal Lu?i
				if ($interface <> "" && $vip['interface'] <> $interface)
1985
					continue;
1986
				$anyproxyarp = true;
1987 abcb2bed Ermal Lu?i
				break;
1988
			case "ipalias":
1989 e5ac67ed Ermal Lu?i
				if ($interface <> "" && $vip['interface'] <> $interface)
1990
					continue;
1991 3dacbd7c Renato Botelho
				interface_ipalias_configure($vip);
1992 abcb2bed Ermal Lu?i
				break;
1993
			case "carp":
1994 e5ac67ed Ermal Lu?i
				if ($interface <> "" && $vip['interface'] <> $interface)
1995
					continue;
1996 bce14123 Ermal
				if ($carp_setuped == false)
1997 abcb2bed Ermal Lu?i
					$carp_setuped = true;
1998
				interface_carp_configure($vip);
1999
				break;
2000 6a74c90e Scott Ullrich
			}
2001 a04de17f Chris Buechler
		}
2002 bce14123 Ermal
		if ($carp_setuped == true)
2003
			interfaces_carp_setup();
2004 e5ac67ed Ermal Lu?i
		if ($anyproxyarp == true)
2005
			interface_proxyarp_configure();
2006 abcb2bed Ermal Lu?i
	}
2007
}
2008
2009
function interface_ipalias_configure(&$vip) {
2010
	if ($vip['mode'] == "ipalias") {
2011
		$if = get_real_interface($vip['interface']);
2012 ce73b2c5 smos
		$af = "inet";
2013
		if(is_ipaddrv6($vip['subnet']))
2014
			$af = "inet6";
2015
		mwexec("/sbin/ifconfig " . escapeshellarg($if) ." {$af} ". escapeshellarg($vip['subnet']) ."/" . escapeshellarg($vip['subnet_bits']) . " alias");
2016 a04de17f Chris Buechler
	}
2017
}
2018
2019 abcb2bed Ermal Lu?i
function interface_reload_carps($cif) {
2020
	global $config;
2021
2022
	$carpifs = link_ip_to_carp_interface(find_interface_ip($cif));
2023 9006e9f8 Scott Ullrich
	if (empty($carpifs))
2024 abcb2bed Ermal Lu?i
		return;
2025
2026
	$carps = explode(" ", $carpifs);
2027
	if(is_array($config['virtualip']['vip'])) {
2028 9006e9f8 Scott Ullrich
		$viparr = &$config['virtualip']['vip'];
2029
		foreach ($viparr as $vip) {
2030 abcb2bed Ermal Lu?i
			if (in_array($vip['carpif'], $carps)) {
2031 9006e9f8 Scott Ullrich
				switch ($vip['mode']) {
2032 89830b60 Ermal
				case "carp":
2033 abcb2bed Ermal Lu?i
					interface_vip_bring_down($vip);
2034
					sleep(1);
2035 9006e9f8 Scott Ullrich
					interface_carp_configure($vip);
2036
					break;
2037 89830b60 Ermal
				case "ipalias":
2038
					interface_vip_bring_down($vip);
2039
					sleep(1);
2040
					interface_ipalias_configure($vip);
2041
					break;
2042 abcb2bed Ermal Lu?i
				}
2043 9006e9f8 Scott Ullrich
			}
2044
		}
2045
	}
2046 abcb2bed Ermal Lu?i
}
2047
2048
function interface_carp_configure(&$vip) {
2049
	global $config, $g;
2050
	if(isset($config['system']['developerspew'])) {
2051 58ebf6bb Scott Ullrich
		$mt = microtime();
2052 0a595d84 Ermal Lu?i
		echo "interface_carp_configure() being called $mt\n";
2053 58ebf6bb Scott Ullrich
	}
2054 abcb2bed Ermal Lu?i
2055
	if ($vip['mode'] != "carp")
2056
		return;
2057
2058
	/*
2059
	 * ensure the interface containing the VIP really exists
2060 1c3ddd9e Renato Botelho
	 * prevents a panic if the interface is missing or invalid
2061 58ebf6bb Scott Ullrich
	 */
2062
	$realif = get_real_interface($vip['interface']);
2063
	if (!does_interface_exist($realif)) {
2064 07e40c1f Carlos Eduardo Ramos
		file_notice("CARP", sprintf(gettext("Interface specified for the virtual IP address %s does not exist. Skipping this VIP."), $vip['subnet']), "Firewall: Virtual IP", "");
2065 58ebf6bb Scott Ullrich
		return;
2066
	}
2067 abcb2bed Ermal Lu?i
2068 3502b5b1 Seth Mos
	if(is_ipaddrv4($vip['subnet'])) {
2069
		/* Ensure CARP IP really exists prior to loading up. */
2070
		$ww_subnet_ip = find_interface_ip($realif);
2071
		$ww_subnet_bits = find_interface_subnet($realif);
2072
		if (!ip_in_subnet($vip['subnet'], gen_subnet($ww_subnet_ip, $ww_subnet_bits) . "/" . $ww_subnet_bits) && !ip_in_interface_alias_subnet($vip['interface'], $vip['subnet'])) {
2073 8b6313a4 jim-p
			file_notice("CARP", sprintf(gettext("Sorry but we could not find a matching real interface subnet for the virtual IP address %s."), $vip['subnet']), "Firewall: Virtual IP", "");
2074 3502b5b1 Seth Mos
			return;
2075
		}
2076
	}
2077
	if(is_ipaddrv6($vip['subnet'])) {
2078
		/* Ensure CARP IP really exists prior to loading up. */
2079
		$ww_subnet_ip = find_interface_ipv6($realif);
2080
		$ww_subnet_bits = find_interface_subnetv6($realif);
2081
		if (!ip_in_subnet($vip['subnet'], gen_subnetv6($ww_subnet_ip, $ww_subnet_bits) . "/" . $ww_subnet_bits) && !ip_in_interface_alias_subnet($vip['interface'], $vip['subnet'])) {
2082 8b6313a4 jim-p
			file_notice("CARP", sprintf(gettext("Sorry but we could not find a matching real interface subnet for the virtual IPv6 address %s."), $vip['subnet']), "Firewall: Virtual IP", "");
2083 3502b5b1 Seth Mos
			return;
2084
		}
2085 f99aa333 Ermal
	}
2086
2087 7b47bd4c Ermal
	// set the vip interface to the vhid
2088
	$vipif = "{$vip['interface']}_vip{$vip['vhid']}";
2089 abcb2bed Ermal Lu?i
2090
	/* create the carp interface and setup */
2091 37a53d16 Scott Ullrich
	if (does_interface_exist($vipif)) {
2092 871768cf Ermal
		pfSense_interface_flags($vipif, -IFF_UP);
2093 37a53d16 Scott Ullrich
	} else {
2094 871768cf Ermal
		$carpif = pfSense_interface_create("carp");
2095
		pfSense_interface_rename($carpif, $vipif);
2096
		pfSense_ngctl_name("{$carpif}:", $vipif);
2097 abcb2bed Ermal Lu?i
	}
2098
2099
	/* invalidate interface cache */
2100
	get_interface_arr(true);
2101
2102 7b47bd4c Ermal
	$vip_password = $vip['password'];
2103
	$vip_password = escapeshellarg(addslashes(str_replace(" ", "", $vip_password)));
2104
	if ($vip['password'] != "")
2105
		$password = " pass {$vip_password}";
2106 a687f866 Namezero
2107 7b47bd4c Ermal
	$broadcast_address = gen_subnet_max($vip['subnet'], $vip['subnet_bits']);
2108 100b7219 Ermal
	$advbase = "";
2109
	if (!empty($vip['advbase']))
2110
		$advbase = "advbase {$vip['advbase']}";
2111 1f74cd2d Seth Mos
2112 3502b5b1 Seth Mos
	if(is_ipaddrv4($vip['subnet'])) {
2113
		$broadcast_address = gen_subnet_max($vip['subnet'], $vip['subnet_bits']);
2114 9caffe86 Seth Mos
		mwexec("/sbin/ifconfig {$vipif} {$vip['subnet']}/{$vip['subnet_bits']} vhid {$vip['vhid']} advskew {$vip['advskew']} {$advbase} {$password}");
2115 3502b5b1 Seth Mos
	}
2116
	if(is_ipaddrv6($vip['subnet'])) {
2117
		$broadcast_address = gen_subnet_max($vip['subnet'], $vip['subnet_bits']);
2118 9caffe86 Seth Mos
		mwexec("/sbin/ifconfig {$vipif} inet6 {$vip['subnet']} prefixlen {$vip['subnet_bits']} vhid {$vip['vhid']} advskew {$vip['advskew']} {$advbase} {$password}");
2119 3502b5b1 Seth Mos
	}
2120 abcb2bed Ermal Lu?i
2121
	interfaces_bring_up($vipif);
2122 7b47bd4c Ermal
2123 abcb2bed Ermal Lu?i
	return $vipif;
2124
}
2125
2126 854aed18 Ermal Lu?i
function interface_wireless_clone($realif, $wlcfg) {
2127 568b1358 Scott Ullrich
	global $config, $g;
2128 be45aa79 Renato Botelho
	/*   Check to see if interface has been cloned as of yet.
2129 88157f66 Scott Ullrich
	 *   If it has not been cloned then go ahead and clone it.
2130
	 */
2131 2a203afd Seth Mos
	$needs_clone = false;
2132 9f428275 Erik Fonnesbeck
	if(is_array($wlcfg['wireless']))
2133
		$wlcfg_mode = $wlcfg['wireless']['mode'];
2134
	else
2135
		$wlcfg_mode = $wlcfg['mode'];
2136
	switch($wlcfg_mode) {
2137 2a203afd Seth Mos
		 case "hostap":
2138
			$mode = "wlanmode hostap";
2139
			break;
2140
		 case "adhoc":
2141
			$mode = "wlanmode adhoc";
2142
			break;
2143
		 default:
2144
			$mode = "";
2145
			break;
2146
	}
2147 34808d4e Erik Fonnesbeck
	$baseif = interface_get_wireless_base($wlcfg['if']);
2148 854aed18 Ermal Lu?i
	if(does_interface_exist($realif)) {
2149
		exec("/sbin/ifconfig {$realif}", $output, $ret);
2150 2a203afd Seth Mos
		$ifconfig_str = implode($output);
2151 9f428275 Erik Fonnesbeck
		if(($wlcfg_mode == "hostap") && (! preg_match("/hostap/si", $ifconfig_str))) {
2152 07e40c1f Carlos Eduardo Ramos
			log_error(sprintf(gettext("Interface %s changed to hostap mode"), $realif));
2153 2a203afd Seth Mos
			$needs_clone = true;
2154
		}
2155 9f428275 Erik Fonnesbeck
		if(($wlcfg_mode == "adhoc") && (! preg_match("/adhoc/si", $ifconfig_str))) {
2156 07e40c1f Carlos Eduardo Ramos
			log_error(sprintf(gettext("Interface %s changed to adhoc mode"), $realif));
2157 2a203afd Seth Mos
			$needs_clone = true;
2158
		}
2159 9f428275 Erik Fonnesbeck
		if(($wlcfg_mode == "bss") && (preg_match("/hostap|adhoc/si", $ifconfig_str))) {
2160 07e40c1f Carlos Eduardo Ramos
			log_error(sprintf(gettext("Interface %s changed to infrastructure mode"), $realif));
2161 2a203afd Seth Mos
			$needs_clone = true;
2162
		}
2163
	} else {
2164
		$needs_clone = true;
2165 88157f66 Scott Ullrich
	}
2166 2a203afd Seth Mos
2167 19e83210 Scott Ullrich
	if($needs_clone == true) {
2168 2a203afd Seth Mos
		/* remove previous instance if it exists */
2169 854aed18 Ermal Lu?i
		if(does_interface_exist($realif))
2170 871768cf Ermal
			pfSense_interface_destroy($realif);
2171 854aed18 Ermal Lu?i
2172 07e40c1f Carlos Eduardo Ramos
		log_error(sprintf(gettext("Cloning new wireless interface %s"), $realif));
2173 b99256c1 Scott Ullrich
		// Create the new wlan interface. FreeBSD returns the new interface name.
2174
		// example:  wlan2
2175 6d54e865 Erik Fonnesbeck
		exec("/sbin/ifconfig wlan create wlandev {$baseif} {$mode} bssid 2>&1", $out, $ret);
2176 2a203afd Seth Mos
		if($ret <> 0) {
2177 addc0439 Renato Botelho
			log_error(sprintf(gettext('Failed to clone interface %1$s with error code %2$s, output %3$s'), $baseif, $ret, $out[0]));
2178 9f428275 Erik Fonnesbeck
			return false;
2179 2a203afd Seth Mos
		}
2180
		$newif = trim($out[0]);
2181
		// Rename the interface to {$parentnic}_wlan{$number}#: EX: ath0_wlan0
2182 871768cf Ermal
		pfSense_interface_rename($newif, $realif);
2183 2a203afd Seth Mos
		// FIXME: not sure what ngctl is for. Doesn't work.
2184 fa71a9b6 Erik Fonnesbeck
		// mwexec("/usr/sbin/ngctl name {$newif}: {$realif}", false);
2185 acb0bce0 Erik Fonnesbeck
		file_put_contents("{$g['tmp_path']}/{$realif}_oldmac", get_interface_mac($realif));
2186 88157f66 Scott Ullrich
	}
2187 9f428275 Erik Fonnesbeck
	return true;
2188 88157f66 Scott Ullrich
}
2189
2190 8f0289e7 Erik Fonnesbeck
function interface_sync_wireless_clones(&$ifcfg, $sync_changes = false) {
2191
	global $config, $g;
2192
2193 56626335 Erik Fonnesbeck
	$shared_settings = array('standard', 'turbo', 'protmode', 'txpower', 'channel',
2194
	                         'diversity', 'txantenna', 'rxantenna', 'distance',
2195
	                         'regdomain', 'regcountry', 'reglocation');
2196 8f0289e7 Erik Fonnesbeck
2197 263e2b7e Erik Fonnesbeck
	if(!is_interface_wireless($ifcfg['if']))
2198 7de319a1 Erik Fonnesbeck
		return;
2199
2200 34808d4e Erik Fonnesbeck
	$baseif = interface_get_wireless_base($ifcfg['if']);
2201 8f0289e7 Erik Fonnesbeck
2202 062023a5 Erik Fonnesbeck
	// Sync shared settings for assigned clones
2203 38b7d47d Erik Fonnesbeck
	$iflist = get_configured_interface_list(false, true);
2204 8f0289e7 Erik Fonnesbeck
	foreach ($iflist as $if) {
2205 34808d4e Erik Fonnesbeck
		if ($baseif == interface_get_wireless_base($config['interfaces'][$if]['if']) && $ifcfg['if'] != $config['interfaces'][$if]['if']) {
2206 8f0289e7 Erik Fonnesbeck
			if (isset($config['interfaces'][$if]['wireless']['standard']) || $sync_changes) {
2207
				foreach ($shared_settings as $setting) {
2208
					if ($sync_changes) {
2209 56626335 Erik Fonnesbeck
						if (isset($ifcfg['wireless'][$setting]))
2210
							$config['interfaces'][$if]['wireless'][$setting] = $ifcfg['wireless'][$setting];
2211
						else if (isset($config['interfaces'][$if]['wireless'][$setting]))
2212
							unset($config['interfaces'][$if]['wireless'][$setting]);
2213 8f0289e7 Erik Fonnesbeck
					} else {
2214 56626335 Erik Fonnesbeck
						if (isset($config['interfaces'][$if]['wireless'][$setting]))
2215
							$ifcfg['wireless'][$setting] = $config['interfaces'][$if]['wireless'][$setting];
2216
						else if (isset($ifcfg['wireless'][$setting]))
2217
							unset($ifcfg['wireless'][$setting]);
2218 8f0289e7 Erik Fonnesbeck
					}
2219
				}
2220
				if (!$sync_changes)
2221
					break;
2222
			}
2223
		}
2224
	}
2225 263e2b7e Erik Fonnesbeck
2226 062023a5 Erik Fonnesbeck
	// Read or write settings at shared area
2227 6ef2297b Erik Fonnesbeck
	if (isset($config['wireless']['interfaces'][$baseif]) && is_array($config['wireless']['interfaces'][$baseif])) {
2228 f62c44d8 Erik Fonnesbeck
		foreach ($shared_settings as $setting) {
2229
			if ($sync_changes) {
2230 56626335 Erik Fonnesbeck
				if (isset($ifcfg['wireless'][$setting]))
2231
					$config['wireless']['interfaces'][$baseif][$setting] = $ifcfg['wireless'][$setting];
2232
				else if (isset($config['wireless']['interfaces'][$baseif][$setting]))
2233
					unset($config['wireless']['interfaces'][$baseif][$setting]);
2234 f62c44d8 Erik Fonnesbeck
			} else if (isset($config['wireless']['interfaces'][$baseif][$setting])) {
2235 56626335 Erik Fonnesbeck
				if (isset($config['wireless']['interfaces'][$baseif][$setting]))
2236
					$ifcfg['wireless'][$setting] = $config['wireless']['interfaces'][$baseif][$setting];
2237
				else if (isset($ifcfg['wireless'][$setting]))
2238
					unset($ifcfg['wireless'][$setting]);
2239 f62c44d8 Erik Fonnesbeck
			}
2240 062023a5 Erik Fonnesbeck
		}
2241
	}
2242
2243
	// Sync the mode on the clone creation page with the configured mode on the interface
2244 6ef2297b Erik Fonnesbeck
	if (interface_is_wireless_clone($ifcfg['if']) && isset($config['wireless']['clone']) && is_array($config['wireless']['clone'])) {
2245 263e2b7e Erik Fonnesbeck
		foreach ($config['wireless']['clone'] as &$clone) {
2246
			if ($clone['cloneif'] == $ifcfg['if']) {
2247
				if ($sync_changes) {
2248
					$clone['mode'] = $ifcfg['wireless']['mode'];
2249
				} else {
2250
					$ifcfg['wireless']['mode'] = $clone['mode'];
2251
				}
2252
				break;
2253
			}
2254
		}
2255 867d444b Erik Fonnesbeck
		unset($clone);
2256 263e2b7e Erik Fonnesbeck
	}
2257 8f0289e7 Erik Fonnesbeck
}
2258
2259 19e83210 Scott Ullrich
function interface_wireless_configure($if, &$wl, &$wlcfg) {
2260 ac3f8318 Espen Johansen
	global $config, $g;
2261 eb772abd Scott Ullrich
2262 4742e927 Scott Ullrich
	/*    open up a shell script that will be used to output the commands.
2263
	 *    since wireless is changing a lot, these series of commands are fragile
2264 905ea336 Phil Davis
	 *    and will sometimes need to be verified by a operator by executing the command
2265
	 *    and returning the output of the command to the developers for inspection.  please
2266
	 *    do not change this routine from a shell script to individual exec commands.  -sullrich
2267 4742e927 Scott Ullrich
	 */
2268 eb772abd Scott Ullrich
2269 b99256c1 Scott Ullrich
	// Remove script file
2270 490b8b2a Scott Ullrich
	unlink_if_exists("{$g['tmp_path']}/{$if}_setup.sh");
2271 eb772abd Scott Ullrich
2272 0a28d385 Erik Fonnesbeck
	// Clone wireless nic if needed.
2273
	interface_wireless_clone($if, $wl);
2274
2275 8f0289e7 Erik Fonnesbeck
	// Reject inadvertent changes to shared settings in case the interface hasn't been configured.
2276
	interface_sync_wireless_clones($wl, false);
2277
2278 6955830f Ermal Lu?i
	$fd_set = fopen("{$g['tmp_path']}/{$if}_setup.sh","w");
2279 4742e927 Scott Ullrich
	fwrite($fd_set, "#!/bin/sh\n");
2280 36d0358b Scott Ullrich
	fwrite($fd_set, "# {$g['product_name']} wireless configuration script.\n\n");
2281 eb772abd Scott Ullrich
2282 2ac908dd Espen Johansen
	/* set values for /path/program */
2283
	$hostapd = "/usr/sbin/hostapd";
2284
	$wpa_supplicant = "/usr/sbin/wpa_supplicant";
2285 4742e927 Scott Ullrich
	$ifconfig = "/sbin/ifconfig";
2286 56626335 Erik Fonnesbeck
	$sysctl = "/sbin/sysctl";
2287 4742e927 Scott Ullrich
	$killall = "/usr/bin/killall";
2288 2ac908dd Espen Johansen
2289 905ea336 Phil Davis
	/* Set all wireless ifconfig variables (split up to get rid of needed checking) */
2290 5508cf57 Scott Ullrich
2291 2a203afd Seth Mos
	$wlcmd = array();
2292 56626335 Erik Fonnesbeck
	$wl_sysctl = array();
2293 2a203afd Seth Mos
	/* Make sure it's up */
2294
	$wlcmd[] = "up";
2295 ac3f8318 Espen Johansen
	/* Set a/b/g standard */
2296 9be20928 Erik Fonnesbeck
	$standard = str_replace(" Turbo", "", $wlcfg['standard']);
2297
	$wlcmd[] = "mode " . escapeshellarg($standard);
2298 2a203afd Seth Mos
2299 5030b5eb Erik Fonnesbeck
	/* XXX: Disable ampdu for now on mwl when running in 11n mode
2300
	 * to prevent massive packet loss under certain conditions. */
2301 9be20928 Erik Fonnesbeck
	if(preg_match("/^mwl/i", $if) && ($standard == "11ng" || $standard == "11na"))
2302 5030b5eb Erik Fonnesbeck
		$wlcmd[] = "-ampdu";
2303
2304 2a203afd Seth Mos
	/* Set ssid */
2305
	if($wlcfg['ssid'])
2306
		$wlcmd[] = "ssid " .escapeshellarg($wlcfg['ssid']);
2307 5508cf57 Scott Ullrich
2308 0856c4ac Scott Ullrich
	/* Set 802.11g protection mode */
2309 2a203afd Seth Mos
	$wlcmd[] = "protmode " . escapeshellarg($wlcfg['protmode']);
2310 0856c4ac Scott Ullrich
2311 ac3f8318 Espen Johansen
	/* set wireless channel value */
2312 2a203afd Seth Mos
	if(isset($wlcfg['channel'])) {
2313
		if($wlcfg['channel'] == "0") {
2314
			$wlcmd[] = "channel any";
2315
		} else {
2316
			$wlcmd[] = "channel " . escapeshellarg($wlcfg['channel']);
2317
		}
2318
	}
2319 2ac908dd Espen Johansen
2320 56626335 Erik Fonnesbeck
	/* Set antenna diversity value */
2321
	if(isset($wlcfg['diversity']))
2322
		$wl_sysctl[] = "diversity=" . escapeshellarg($wlcfg['diversity']);
2323
2324
	/* Set txantenna value */
2325
	if(isset($wlcfg['txantenna']))
2326
		$wl_sysctl[] = "txantenna=" . escapeshellarg($wlcfg['txantenna']);
2327
2328
	/* Set rxantenna value */
2329
	if(isset($wlcfg['rxantenna']))
2330
		$wl_sysctl[] = "rxantenna=" . escapeshellarg($wlcfg['rxantenna']);
2331
2332 f134033e Scott Ullrich
	/* set Distance value */
2333 eb772abd Scott Ullrich
	if($wlcfg['distance'])
2334 f134033e Scott Ullrich
		$distance = escapeshellarg($wlcfg['distance']);
2335
2336 ac3f8318 Espen Johansen
	/* Set wireless hostap mode */
2337 2a203afd Seth Mos
	if ($wlcfg['mode'] == "hostap") {
2338
		$wlcmd[] = "mediaopt hostap";
2339
	} else {
2340
		$wlcmd[] = "-mediaopt hostap";
2341
	}
2342 ac3f8318 Espen Johansen
2343
	/* Set wireless adhoc mode */
2344 2a203afd Seth Mos
	if ($wlcfg['mode'] == "adhoc") {
2345
		$wlcmd[] = "mediaopt adhoc";
2346
	} else {
2347
		$wlcmd[] = "-mediaopt adhoc";
2348
	}
2349 ac3f8318 Espen Johansen
2350
	/* Not neccesary to set BSS mode as this is default if adhoc and/or hostap is NOT set */
2351
2352
	/* handle hide ssid option */
2353 2a203afd Seth Mos
	if(isset($wlcfg['hidessid']['enable'])) {
2354
		$wlcmd[] = "hidessid";
2355
	} else {
2356
		$wlcmd[] = "-hidessid";
2357
	}
2358 ac3f8318 Espen Johansen
2359
	/* handle pureg (802.11g) only option */
2360 2a203afd Seth Mos
	if(isset($wlcfg['pureg']['enable'])) {
2361
		$wlcmd[] = "mode 11g pureg";
2362
	} else {
2363
		$wlcmd[] = "-pureg";
2364
	}
2365 ac3f8318 Espen Johansen
2366 ed459692 Erik Fonnesbeck
	/* handle puren (802.11n) only option */
2367
	if(isset($wlcfg['puren']['enable'])) {
2368
		$wlcmd[] = "puren";
2369
	} else {
2370
		$wlcmd[] = "-puren";
2371
	}
2372
2373 ac3f8318 Espen Johansen
	/* enable apbridge option */
2374 2a203afd Seth Mos
	if(isset($wlcfg['apbridge']['enable'])) {
2375
		$wlcmd[] = "apbridge";
2376
	} else {
2377
		$wlcmd[] = "-apbridge";
2378
	}
2379 ac3f8318 Espen Johansen
2380
	/* handle turbo option */
2381 2a203afd Seth Mos
	if(isset($wlcfg['turbo']['enable'])) {
2382
		$wlcmd[] = "mediaopt turbo";
2383
	} else {
2384
		$wlcmd[] = "-mediaopt turbo";
2385
	}
2386 ac3f8318 Espen Johansen
2387
	/* handle txpower setting */
2388 2a203afd Seth Mos
	/* if($wlcfg['txpower'] <> "")
2389
		$wlcmd[] = "txpower " . escapeshellarg($wlcfg['txpower']);
2390
	*/
2391 ac3f8318 Espen Johansen
	/* handle wme option */
2392 2a203afd Seth Mos
	if(isset($wlcfg['wme']['enable'])) {
2393
		$wlcmd[] = "wme";
2394
	} else {
2395
		$wlcmd[] = "-wme";
2396
	}
2397 eb772abd Scott Ullrich
2398 ac3f8318 Espen Johansen
	/* set up wep if enabled */
2399 2a203afd Seth Mos
	$wepset = "";
2400
	if (isset($wlcfg['wep']['enable']) && is_array($wlcfg['wep']['key'])) {
2401
		switch($wlcfg['wpa']['auth_algs']) {
2402
			case "1":
2403
				$wepset .= "authmode open wepmode on ";
2404
				break;
2405
			case "2":
2406
				$wepset .= "authmode shared wepmode on ";
2407
				break;
2408
			case "3":
2409
				$wepset .= "authmode mixed wepmode on ";
2410
		}
2411 2f19fa14 Scott Ullrich
		$i = 1;
2412
		foreach ($wlcfg['wep']['key'] as $wepkey) {
2413
			$wepset .= "wepkey " . escapeshellarg("{$i}:{$wepkey['value']}") . " ";
2414 2a203afd Seth Mos
			if (isset($wepkey['txkey'])) {
2415
				$wlcmd[] = "weptxkey {$i} ";
2416
			}
2417 2f19fa14 Scott Ullrich
			$i++;
2418
		}
2419 2a203afd Seth Mos
		$wlcmd[] = $wepset;
2420
	} else {
2421
		$wlcmd[] = "authmode open wepmode off ";
2422 ac3f8318 Espen Johansen
	}
2423
2424 97f3ce0f Phil Davis
	kill_hostapd($if);
2425 c8178bb7 Erik Fonnesbeck
	mwexec(kill_wpasupplicant("{$if}"));
2426
2427 ac3f8318 Espen Johansen
	/* generate wpa_supplicant/hostap config if wpa is enabled */
2428 2a203afd Seth Mos
	conf_mount_rw();
2429 ac3f8318 Espen Johansen
2430
	switch ($wlcfg['mode']) {
2431 b67d192d Scott Ullrich
		case 'bss':
2432 ac3f8318 Espen Johansen
			if (isset($wlcfg['wpa']['enable'])) {
2433
				$wpa .= <<<EOD
2434 454756b9 Scott Ullrich
ctrl_interface={$g['varrun_path']}/wpa_supplicant
2435 50ad3b7c Scott Ullrich
ctrl_interface_group=0
2436
ap_scan=1
2437 2ac908dd Espen Johansen
#fast_reauth=1
2438 249558a2 Scott Ullrich
network={
2439 454756b9 Scott Ullrich
ssid="{$wlcfg['ssid']}"
2440
scan_ssid=1
2441 2ac908dd Espen Johansen
priority=5
2442
key_mgmt={$wlcfg['wpa']['wpa_key_mgmt']}
2443 454756b9 Scott Ullrich
psk="{$wlcfg['wpa']['passphrase']}"
2444 2ac908dd Espen Johansen
pairwise={$wlcfg['wpa']['wpa_pairwise']}
2445
group={$wlcfg['wpa']['wpa_pairwise']}
2446 50ad3b7c Scott Ullrich
}
2447
EOD;
2448
2449 80ec5eaa Scott Ullrich
				$fd = fopen("{$g['varetc_path']}/wpa_supplicant_{$if}.conf", "w");
2450 ac3f8318 Espen Johansen
				fwrite($fd, "{$wpa}");
2451
				fclose($fd);
2452
			}
2453 2a203afd Seth Mos
			break;
2454 ac3f8318 Espen Johansen
		case 'hostap':
2455 be45aa79 Renato Botelho
			if($wlcfg['wpa']['passphrase'])
2456 7eadaa9c Scott Ullrich
				$wpa_passphrase = "wpa_passphrase={$wlcfg['wpa']['passphrase']}\n";
2457 be45aa79 Renato Botelho
			else
2458 abfd0c9b Scott Ullrich
				$wpa_passphrase = "";
2459 ac3f8318 Espen Johansen
			if (isset($wlcfg['wpa']['enable'])) {
2460
				$wpa .= <<<EOD
2461 459d6351 Scott Ullrich
interface={$if}
2462
driver=bsd
2463
logger_syslog=-1
2464
logger_syslog_level=0
2465
logger_stdout=-1
2466
logger_stdout_level=0
2467 2ac908dd Espen Johansen
dump_file={$g['tmp_path']}/hostapd_{$if}.dump
2468
ctrl_interface={$g['varrun_path']}/hostapd
2469 459d6351 Scott Ullrich
ctrl_interface_group=wheel
2470 2ac908dd Espen Johansen
#accept_mac_file={$g['tmp_path']}/hostapd_{$if}.accept
2471
#deny_mac_file={$g['tmp_path']}/hostapd_{$if}.deny
2472 b67d192d Scott Ullrich
#macaddr_acl={$wlcfg['wpa']['macaddr_acl']}
2473 459d6351 Scott Ullrich
ssid={$wlcfg['ssid']}
2474 2ac908dd Espen Johansen
debug={$wlcfg['wpa']['debug_mode']}
2475
auth_algs={$wlcfg['wpa']['auth_algs']}
2476
wpa={$wlcfg['wpa']['wpa_mode']}
2477
wpa_key_mgmt={$wlcfg['wpa']['wpa_key_mgmt']}
2478
wpa_pairwise={$wlcfg['wpa']['wpa_pairwise']}
2479 ac3f8318 Espen Johansen
wpa_group_rekey={$wlcfg['wpa']['wpa_group_rekey']}
2480
wpa_gmk_rekey={$wlcfg['wpa']['wpa_gmk_rekey']}
2481
wpa_strict_rekey={$wlcfg['wpa']['wpa_strict_rekey']}
2482 7eadaa9c Scott Ullrich
{$wpa_passphrase}
2483 525d565b Scott Ullrich
2484 459d6351 Scott Ullrich
EOD;
2485 2ac908dd Espen Johansen
2486 c9e7d30d Scott Ullrich
if (isset($wlcfg['wpa']['rsn_preauth'])) {
2487
	$wpa .= <<<EOD
2488
# Enable the next lines for preauth when roaming. Interface = wired or wireless interface talking to the AP you want to roam from/to
2489
rsn_preauth=1
2490
rsn_preauth_interfaces={$if}
2491
2492
EOD;
2493
2494
}
2495 5949124c Scott Ullrich
				if($wlcfg['auth_server_addr'] && $wlcfg['auth_server_shared_secret']) {
2496
					$auth_server_port = "1812";
2497 be45aa79 Renato Botelho
					if($wlcfg['auth_server_port'])
2498 5949124c Scott Ullrich
						$auth_server_port = $wlcfg['auth_server_port'];
2499 a687f866 Namezero
					$auth_server_port2 = "1812";
2500 be45aa79 Renato Botelho
					if($wlcfg['auth_server_port2'])
2501 a687f866 Namezero
						$auth_server_port2 = $wlcfg['auth_server_port2'];
2502 5949124c Scott Ullrich
					$wpa .= <<<EOD
2503 525d565b Scott Ullrich
2504 5949124c Scott Ullrich
ieee8021x=1
2505
auth_server_addr={$wlcfg['auth_server_addr']}
2506
auth_server_port={$auth_server_port}
2507
auth_server_shared_secret={$wlcfg['auth_server_shared_secret']}
2508 a687f866 Namezero
auth_server_addr={$wlcfg['auth_server_addr2']}
2509
auth_server_port={$auth_server_port2}
2510
auth_server_shared_secret={$wlcfg['auth_server_shared_secret2']}
2511 525d565b Scott Ullrich
2512 459d6351 Scott Ullrich
EOD;
2513 5949124c Scott Ullrich
				} else {
2514
					$wpa .= "ieee8021x={$wlcfg['wpa']['ieee8021x']}\n";
2515
				}
2516 2ac908dd Espen Johansen
2517 80ec5eaa Scott Ullrich
				$fd = fopen("{$g['varetc_path']}/hostapd_{$if}.conf", "w");
2518 ac3f8318 Espen Johansen
				fwrite($fd, "{$wpa}");
2519
				fclose($fd);
2520 2ac908dd Espen Johansen
2521 ac3f8318 Espen Johansen
			}
2522 2a203afd Seth Mos
			break;
2523 eb772abd Scott Ullrich
	}
2524 ac3f8318 Espen Johansen
2525 4742e927 Scott Ullrich
	/*
2526
	 *    all variables are set, lets start up everything
2527 2a203afd Seth Mos
	 */
2528 eb772abd Scott Ullrich
2529 bbfc810e Erik Fonnesbeck
	$baseif = interface_get_wireless_base($if);
2530 56626335 Erik Fonnesbeck
	preg_match("/^(.*?)([0-9]*)$/", $baseif, $baseif_split);
2531
	$wl_sysctl_prefix = 'dev.' . $baseif_split[1] . '.' . $baseif_split[2];
2532
2533
	/* set sysctls for the wireless interface */
2534
	if (!empty($wl_sysctl)) {
2535
		fwrite($fd_set, "# sysctls for {$baseif}\n");
2536
		foreach ($wl_sysctl as $wl_sysctl_line) {
2537
			fwrite($fd_set, "{$sysctl} {$wl_sysctl_prefix}.{$wl_sysctl_line}\n");
2538
		}
2539
	}
2540 bbfc810e Erik Fonnesbeck
2541 78922914 Scott Ullrich
	/* set ack timers according to users preference (if he/she has any) */
2542
	if($distance) {
2543 4742e927 Scott Ullrich
		fwrite($fd_set, "# Enable ATH distance settings\n");
2544 e327021d Erik Fonnesbeck
		fwrite($fd_set, "/sbin/athctrl.sh -i {$baseif} -d {$distance}\n");
2545 78922914 Scott Ullrich
	}
2546 eb772abd Scott Ullrich
2547 ac3f8318 Espen Johansen
	if (isset($wlcfg['wpa']['enable'])) {
2548 2a203afd Seth Mos
		if ($wlcfg['mode'] == "bss") {
2549 4742e927 Scott Ullrich
			fwrite($fd_set, "{$wpa_supplicant} -B -i {$if} -c {$g['varetc_path']}/wpa_supplicant_{$if}.conf\n");
2550 2a203afd Seth Mos
		}
2551
		if ($wlcfg['mode'] == "hostap") {
2552 864bf774 Erik Fonnesbeck
			/* add line to script to restore old mac to make hostapd happy */
2553 acb0bce0 Erik Fonnesbeck
			if (file_exists("{$g['tmp_path']}/{$if}_oldmac")) {
2554
				$if_oldmac = file_get_contents("{$g['tmp_path']}/{$if}_oldmac");
2555
				if (is_macaddr($if_oldmac))
2556
					fwrite($fd_set, "{$ifconfig} " . escapeshellarg($if) .
2557
						" link " . escapeshellarg($if_oldmac) . "\n");
2558
			}
2559
2560 97f3ce0f Phil Davis
			fwrite($fd_set, "{$hostapd} -B -P {$g['varrun_path']}/hostapd_{$if}.pid {$g['varetc_path']}/hostapd_{$if}.conf\n");
2561 864bf774 Erik Fonnesbeck
2562
			/* add line to script to restore spoofed mac after running hostapd */
2563
			if (file_exists("{$g['tmp_path']}/{$if}_oldmac")) {
2564
				if ($wl['spoofmac'])
2565
					$if_curmac = $wl['spoofmac'];
2566
				else
2567
					$if_curmac = get_interface_mac($if);
2568
				if (is_macaddr($if_curmac))
2569
					fwrite($fd_set, "{$ifconfig} " . escapeshellarg($if) .
2570
						" link " . escapeshellarg($if_curmac) . "\n");
2571
			}
2572 2a203afd Seth Mos
		}
2573 ac3f8318 Espen Johansen
	}
2574 191a8175 Scott Ullrich
2575 4742e927 Scott Ullrich
	fclose($fd_set);
2576 8a958125 Scott Ullrich
	conf_mount_ro();
2577
2578 bbfc810e Erik Fonnesbeck
	/* Making sure regulatory settings have actually changed
2579
	 * before applying, because changing them requires bringing
2580
	 * down all wireless networks on the interface. */
2581
	exec("{$ifconfig} " . escapeshellarg($if), $output);
2582
	$ifconfig_str = implode($output);
2583
	unset($output);
2584
	$reg_changing = false;
2585
2586 89e7778f Erik Fonnesbeck
	/* special case for the debug country code */
2587
	if ($wlcfg['regcountry'] == 'DEBUG' && !preg_match("/\sregdomain\s+DEBUG\s/si", $ifconfig_str))
2588
		$reg_changing = true;
2589
	else if ($wlcfg['regdomain'] && !preg_match("/\sregdomain\s+{$wlcfg['regdomain']}\s/si", $ifconfig_str))
2590 bbfc810e Erik Fonnesbeck
		$reg_changing = true;
2591
	else if ($wlcfg['regcountry'] && !preg_match("/\scountry\s+{$wlcfg['regcountry']}\s/si", $ifconfig_str))
2592
		$reg_changing = true;
2593 89e7778f Erik Fonnesbeck
	else if ($wlcfg['reglocation'] == 'anywhere' && preg_match("/\s(indoor|outdoor)\s/si", $ifconfig_str))
2594
		$reg_changing = true;
2595 06cb2656 Erik Fonnesbeck
	else if ($wlcfg['reglocation'] && $wlcfg['reglocation'] != 'anywhere' && !preg_match("/\s{$wlcfg['reglocation']}\s/si", $ifconfig_str))
2596 bbfc810e Erik Fonnesbeck
		$reg_changing = true;
2597
2598
	if ($reg_changing) {
2599
		/* set regulatory domain */
2600
		if($wlcfg['regdomain'])
2601
			$wlregcmd[] = "regdomain " . escapeshellarg($wlcfg['regdomain']);
2602
2603
		/* set country */
2604
		if($wlcfg['regcountry'])
2605
			$wlregcmd[] = "country " . escapeshellarg($wlcfg['regcountry']);
2606
2607
		/* set location */
2608
		if($wlcfg['reglocation'])
2609
			$wlregcmd[] = escapeshellarg($wlcfg['reglocation']);
2610
2611
		$wlregcmd_args = implode(" ", $wlregcmd);
2612
2613
		/* build a complete list of the wireless clones for this interface */
2614
		$clone_list = array();
2615
		if (does_interface_exist(interface_get_wireless_clone($baseif)))
2616
			$clone_list[] = interface_get_wireless_clone($baseif);
2617 6ef2297b Erik Fonnesbeck
		if (isset($config['wireless']['clone']) && is_array($config['wireless']['clone'])) {
2618 bbfc810e Erik Fonnesbeck
			foreach ($config['wireless']['clone'] as $clone) {
2619
				if ($clone['if'] == $baseif)
2620
					$clone_list[] = $clone['cloneif'];
2621
			}
2622
		}
2623
2624
		/* find which clones are up and bring them down */
2625
		$clones_up = array();
2626
		foreach ($clone_list as $clone_if) {
2627 1cf76394 Erik Fonnesbeck
			$clone_status = pfSense_get_interface_addresses($clone_if);
2628 bbfc810e Erik Fonnesbeck
			if ($clone_status['status'] == 'up') {
2629
				$clones_up[] = $clone_if;
2630
				mwexec("{$ifconfig} " . escapeshellarg($clone_if) . " down");
2631
			}
2632
		}
2633
2634
		/* apply the regulatory settings */
2635
		mwexec("{$ifconfig} " . escapeshellarg($if) . " {$wlregcmd_args}");
2636
2637
		/* bring the clones back up that were previously up */
2638
		foreach ($clones_up as $clone_if) {
2639
			mwexec("{$ifconfig} " . escapeshellarg($clone_if) . " up");
2640 67e77adf Erik Fonnesbeck
2641
			/*
2642
			 * Rerun the setup script for the interface if it isn't this interface, the interface
2643
			 * is in infrastructure mode, and WPA is enabled.
2644
			 * This can be removed if wpa_supplicant stops dying when you bring the interface down.
2645
			 */
2646
			if ($clone_if != $if) {
2647
				$friendly_if = convert_real_interface_to_friendly_interface_name($clone_if);
2648
				if ( !empty($friendly_if)
2649
				    && $config['interfaces'][$friendly_if]['wireless']['mode'] == "bss"
2650
				    && isset($config['interfaces'][$friendly_if]['wireless']['wpa']['enable']) ) {
2651
					mwexec("/bin/sh {$g['tmp_path']}/{$clone_if}_setup.sh");
2652
				}
2653
			}
2654 bbfc810e Erik Fonnesbeck
		}
2655
	}
2656
2657 23fdc06e Erik Fonnesbeck
	/* The mode must be specified in a separate command before ifconfig
2658
	 * will allow the mode and channel at the same time in the next. */
2659 9be20928 Erik Fonnesbeck
	mwexec("/sbin/ifconfig {$if} mode " . escapeshellarg($standard));
2660 23fdc06e Erik Fonnesbeck
2661 2a48a885 Erik Fonnesbeck
	/* configure wireless */
2662
	$wlcmd_args = implode(" ", $wlcmd);
2663
	mwexec("/sbin/ifconfig {$if} $wlcmd_args", false);
2664
2665 be45aa79 Renato Botelho
2666 2a203afd Seth Mos
	sleep(1);
2667
	/* execute hostapd and wpa_supplicant if required in shell */
2668 6955830f Ermal Lu?i
	mwexec("/bin/sh {$g['tmp_path']}/{$if}_setup.sh");
2669 191a8175 Scott Ullrich
2670 ac3f8318 Espen Johansen
	return 0;
2671 cfc707f7 Scott Ullrich
2672 5b237745 Scott Ullrich
}
2673
2674 eba938e3 Scott Ullrich
function kill_hostapd($interface) {
2675 97f3ce0f Phil Davis
	global $g;
2676
2677
	if (isvalidpid("{$g['varrun_path']}/hostapd_{$interface}.pid"))
2678
		return killbypid("{$g['varrun_path']}/hostapd_{$interface}.pid");
2679 4b2a6180 Scott Ullrich
}
2680
2681 eba938e3 Scott Ullrich
function kill_wpasupplicant($interface) {
2682 31b958d5 Erik Fonnesbeck
	return "/bin/pkill -f \"wpa_supplicant .*{$interface}\\.conf\"\n";
2683 4b2a6180 Scott Ullrich
}
2684
2685 eba938e3 Scott Ullrich
function find_dhclient_process($interface) {
2686 319cbd5e Ermal
	if ($interface)
2687 05c4bfa0 Ermal
		$pid = `/bin/pgrep -axf "dhclient: {$interface}"`;
2688 319cbd5e Ermal
	else
2689
		$pid = 0;
2690
2691 bcfe4ae5 Ermal
	return intval($pid);
2692 0311dbd5 Scott Ullrich
}
2693
2694 1af4f4e0 Ermal
function find_rtsold_process($interface) {
2695
	global $g;
2696
2697
	if ($interface)
2698
		if (isvalidpid("{$g['varrun_path']}/rtsold_{$interface}.pid"))
2699
			$pid = trim(file_get_contents("{$g['varrun_path']}/rtsold_{$interface}.pid"), " \n");
2700
	else
2701
		return(false);
2702
2703
	return intval($pid);
2704
}
2705
2706 c495f88b Seth Mos
function find_dhcp6c_process($interface) {
2707 b0059636 Ermal
	global $g;
2708
2709 c495f88b Seth Mos
	if ($interface)
2710 b0059636 Ermal
		if (isvalidpid("{$g['varrun_path']}/dhcp6c_{$interface}.pid"))
2711
			$pid = trim(file_get_contents("{$g['varrun_path']}/dhcp6c_{$interface}.pid"), " \n");
2712 c495f88b Seth Mos
	else
2713 74fa57aa smos
		return(false);
2714 c495f88b Seth Mos
2715
	return intval($pid);
2716
}
2717
2718 4ffa46bf Ermal
function interface_vlan_mtu_configured($realhwif, $mtu) {
2719
	global $config;
2720
2721
	if (is_array($config['vlans']['vlan'])) {
2722
		foreach ($config['vlans']['vlan'] as $vlan) {
2723
			if ($vlan['if'] != $realhwif)
2724
				continue;
2725 a1d36777 Renato Botelho
			$assignedport = convert_real_interface_to_friendly_interface_name($vlan['vlanif']);
2726
			if (!empty($assignedport)) {
2727
				$portmtu = $config['interfaces'][$assignedport]['mtu'];
2728 4ffa46bf Ermal
				if (!empty($portmtu) && $portmtu > $mtu)
2729
					$mtu = $portmtu;
2730
			}
2731
		}
2732
	}
2733
2734
	return $mtu;
2735
}
2736
2737 7413cbfd Ermal
function interface_configure($interface = "wan", $reloadall = false, $linkupevent = false) {
2738 675aac3d Ermal Luçi
	global $config, $g;
2739 31b24870 Ermal Luçi
	global $interface_sn_arr_cache, $interface_ip_arr_cache;
2740 3502b5b1 Seth Mos
	global $interface_snv6_arr_cache, $interface_ipv6_arr_cache;
2741 cfc707f7 Scott Ullrich
2742 67ee1ec5 Ermal Luçi
	$wancfg = $config['interfaces'][$interface];
2743
2744 e017a46a Ermal
	if (!isset($wancfg['enable']))
2745
		return;
2746
2747 85a5da13 Ermal Luçi
	$realif = get_real_interface($interface);
2748 20cb9803 gnhb
	$realhwif_array = get_parent_interface($interface);
2749
	// Need code to handle MLPPP if we ever use $realhwif for MLPPP handling
2750
	$realhwif = $realhwif_array[0];
2751 cfc707f7 Scott Ullrich
2752 5a3031ea smos
	/* Disable Accepting router advertisements unless specifically requested */
2753 9cd6b950 Ermal
	if ($g['debug'])
2754
		log_error("Deny router advertisements for interface {$interface}");
2755 5a3031ea smos
	mwexec("/sbin/ifconfig " . escapeshellarg($realif) . " inet6 -accept_rtadv");
2756 be45aa79 Renato Botelho
2757 f382c6de Ermal
	if (!$g['booting'] && !(substr($realif, 0, 4) == "ovpn")) {
2758 3c5e10fc Seth Mos
		/* remove all IPv4 and IPv6 addresses */
2759 332683cb Seth Mos
		while (mwexec("/sbin/ifconfig " . escapeshellarg($realif) . " -alias", true) == 0);
2760 3502b5b1 Seth Mos
		while (mwexec("/sbin/ifconfig " . escapeshellarg($realif) . " inet6 -alias", true) == 0);
2761 3896d93e Erik Fonnesbeck
2762 8103bd1e Seth Mos
		/* only bring down the interface when both v4 and v6 are set to NONE */
2763 733829a9 Renato Botelho
		if(empty($wancfg['ipaddr']) && empty($wancfg['ipaddrv6'])) {
2764 8103bd1e Seth Mos
			interface_bring_down($interface);
2765 3896d93e Erik Fonnesbeck
		}
2766 28d22199 Scott Ullrich
	}
2767 acc1e9d0 Scott Ullrich
2768 0a28d385 Erik Fonnesbeck
	/* wireless configuration? */
2769 5b237745 Scott Ullrich
	if (is_array($wancfg['wireless']))
2770 0a28d385 Erik Fonnesbeck
		interface_wireless_configure($realif, $wancfg, $wancfg['wireless']);
2771 cfc707f7 Scott Ullrich
2772 49db607f jim-p
	$mac = get_interface_mac($realhwif);
2773 1489e8c8 Renato Botelho
	/*
2774
	 * Don't try to reapply the spoofed MAC if it's already applied.
2775
	 * When ifconfig link is used, it cycles the interface down/up, which triggers
2776
	 * the interface config again, which attempts to spoof the MAC again,
2777
	 * which cycles the link again...
2778
	 */
2779 49db607f jim-p
	if ($wancfg['spoofmac'] && ($wancfg['spoofmac'] != $mac)) {
2780 3e5d0d1d Ermal
		mwexec("/sbin/ifconfig " . escapeshellarg($realhwif) .
2781 5b237745 Scott Ullrich
			" link " . escapeshellarg($wancfg['spoofmac']));
2782 ac8ff0a4 Ermal
2783 1489e8c8 Renato Botelho
		/*
2784
		 * All vlans need to spoof their parent mac address, too.  see
2785
		 * ticket #1514: http://cvstrac.pfsense.com/tktview?tn=1514,33
2786
		 */
2787
		if (is_array($config['vlans']['vlan'])) {
2788
			foreach ($config['vlans']['vlan'] as $vlan) {
2789
				if ($vlan['if'] == $realhwif)
2790
					mwexec("/sbin/ifconfig " . escapeshellarg($vlan['vlanif']) .
2791
					" link " . escapeshellarg($wancfg['spoofmac']));
2792
			}
2793
		}
2794 f36d4bd2 Scott Ullrich
	}  else {
2795 a687f866 Namezero
2796 3e5d0d1d Ermal
		if ($mac == "ff:ff:ff:ff:ff:ff") {
2797 f36d4bd2 Scott Ullrich
			/*   this is not a valid mac address.  generate a
2798
			 *   temporary mac address so the machine can get online.
2799
			 */
2800 07e40c1f Carlos Eduardo Ramos
			echo gettext("Generating new MAC address.");
2801 f36d4bd2 Scott Ullrich
			$random_mac = generate_random_mac_address();
2802 3e5d0d1d Ermal
			mwexec("/sbin/ifconfig " . escapeshellarg($realhwif) .
2803 f36d4bd2 Scott Ullrich
				" link " . escapeshellarg($random_mac));
2804
			$wancfg['spoofmac'] = $random_mac;
2805
			write_config();
2806 addc0439 Renato Botelho
			file_notice("MAC Address altered", sprintf(gettext('The INVALID MAC address (ff:ff:ff:ff:ff:ff) on interface %1$s has been automatically replaced with %2$s'), $realif, $random_mac), "Interfaces");
2807 f36d4bd2 Scott Ullrich
		}
2808
	}
2809 cfc707f7 Scott Ullrich
2810 5b237745 Scott Ullrich
	/* media */
2811
	if ($wancfg['media'] || $wancfg['mediaopt']) {
2812 3e5d0d1d Ermal
		$cmd = "/sbin/ifconfig " . escapeshellarg($realhwif);
2813 5b237745 Scott Ullrich
		if ($wancfg['media'])
2814
			$cmd .= " media " . escapeshellarg($wancfg['media']);
2815
		if ($wancfg['mediaopt'])
2816
			$cmd .= " mediaopt " . escapeshellarg($wancfg['mediaopt']);
2817
		mwexec($cmd);
2818
	}
2819 3e5d0d1d Ermal
	$options = pfSense_get_interface_addresses($realhwif);
2820 9a4c3eed Ermal
	if (is_array($options) && isset($options['caps']['polling'])) {
2821
		if (isset($config['system']['polling']))
2822
			pfSense_interface_capabilities($realif, IFCAP_POLLING);
2823
		else
2824
			pfSense_interface_capabilities($realif, -IFCAP_POLLING);
2825
	}
2826
2827 51d5aad7 Ermal
	/* skip vlans for checksumming and polling */
2828 7965c38f Ermal
	if (!stristr($realif, "_vlan") && is_array($options)) {
2829 51d5aad7 Ermal
		$flags = 0;
2830
		if(isset($config['system']['disablechecksumoffloading'])) {
2831
			if (isset($options['encaps']['txcsum']))
2832
				$flags |= IFCAP_TXCSUM;
2833
			if (isset($options['encaps']['rxcsum']))
2834
				$flags |= IFCAP_RXCSUM;
2835 1489e8c8 Renato Botelho
		} else {
2836
			if (!isset($options['caps']['txcsum']))
2837 51d5aad7 Ermal
				$flags |= IFCAP_TXCSUM;
2838
			if (!isset($options['caps']['rxcsum']))
2839
				$flags |= IFCAP_RXCSUM;
2840 1489e8c8 Renato Botelho
		}
2841 51d5aad7 Ermal
2842 1489e8c8 Renato Botelho
		if(isset($config['system']['disablesegmentationoffloading'])) {
2843
			if (isset($options['encaps']['tso4']))
2844 51d5aad7 Ermal
				$flags |= IFCAP_TSO;
2845 1489e8c8 Renato Botelho
			if (isset($options['encaps']['tso6']))
2846 51d5aad7 Ermal
				$flags |= IFCAP_TSO;
2847 1489e8c8 Renato Botelho
		} else {
2848
			if (!isset($options['caps']['tso4']))
2849 51d5aad7 Ermal
				$flags |= IFCAP_TSO;
2850 1489e8c8 Renato Botelho
			if (!isset($options['caps']['tso6']))
2851 51d5aad7 Ermal
				$flags |= IFCAP_TSO;
2852 1489e8c8 Renato Botelho
		}
2853 51d5aad7 Ermal
2854 1489e8c8 Renato Botelho
		if(isset($config['system']['disablelargereceiveoffloading'])) {
2855
			if (isset($options['encaps']['lro']))
2856 51d5aad7 Ermal
				$flags |= IFCAP_LRO;
2857 1489e8c8 Renato Botelho
		} else {
2858
			if (!isset($options['caps']['lro']))
2859 51d5aad7 Ermal
				$flags |= IFCAP_LRO;
2860 1489e8c8 Renato Botelho
		}
2861 51d5aad7 Ermal
2862 1489e8c8 Renato Botelho
		/* if the NIC supports polling *AND* it is enabled in the GUI */
2863
		if (!isset($config['system']['polling']) || !isset($options['caps']['polling'])) {
2864 51d5aad7 Ermal
			$flags |= IFCAP_POLLING;
2865
		}
2866 1489e8c8 Renato Botelho
		pfSense_interface_capabilities($realhwif, -$flags);
2867 51d5aad7 Ermal
	}
2868
2869 31b24870 Ermal Luçi
	/* invalidate interface/ip/sn cache */
2870 eba938e3 Scott Ullrich
	get_interface_arr(true);
2871 31b24870 Ermal Luçi
	unset($interface_ip_arr_cache[$realif]);
2872
	unset($interface_sn_arr_cache[$realif]);
2873 5a5413bb Seth Mos
	unset($interface_ipv6_arr_cache[$realif]);
2874
	unset($interface_snv6_arr_cache[$realif]);
2875 ccbd2447 Ermal Luçi
2876 5b237745 Scott Ullrich
	switch ($wancfg['ipaddr']) {
2877
		case 'dhcp':
2878 1fb7c265 Ermal Luçi
			interface_dhcp_configure($interface);
2879 5b237745 Scott Ullrich
			break;
2880
		case 'pppoe':
2881 8af6c46d gnhb
		case 'l2tp':
2882 5b237745 Scott Ullrich
		case 'pptp':
2883 9ebe7028 gnhb
		case 'ppp':
2884 64d124c5 gnhb
			interface_ppps_configure($interface);
2885 9ebe7028 gnhb
			break;
2886 5b237745 Scott Ullrich
		default:
2887 8103bd1e Seth Mos
			if (is_ipaddr($wancfg['ipaddr']) && $wancfg['subnet'] <> "") {
2888 871768cf Ermal
				pfSense_interface_setaddress($realif, "{$wancfg['ipaddr']}/{$wancfg['subnet']}");
2889 d1eea523 Ermal
			} else if (substr($realif, 0, 3) == "gre") {
2890
				if (is_array($config['gres']['gre'])) {
2891
					foreach ($config['gres']['gre'] as $gre)
2892
						if ($gre['greif'] == $realif)
2893
							interface_gre_configure($gre);
2894
				}
2895
			} else if (substr($realif, 0, 3) == "gif") {
2896 1489e8c8 Renato Botelho
				if (is_array($config['gifs']['gif'])) {
2897 d1eea523 Ermal
					foreach ($config['gifs']['gif'] as $gif)
2898 d1ae9705 Ermal
						if($gif['gifif'] == $realif)
2899 d1eea523 Ermal
							interface_gif_configure($gif);
2900
				}
2901
			} else if (substr($realif, 0, 4) == "ovpn") {
2902
				/* XXX: Should be done anything?! */
2903 acc1e9d0 Scott Ullrich
			}
2904 d1eea523 Ermal
			break;
2905 5b237745 Scott Ullrich
	}
2906 ffeb5acf Scott Ullrich
2907 5a5413bb Seth Mos
	switch ($wancfg['ipaddrv6']) {
2908 feb88a14 smos
		case 'slaac':
2909 8103bd1e Seth Mos
		case 'dhcp6':
2910 7a04cd20 Ermal
			interface_dhcpv6_configure($interface, $wancfg);
2911 8103bd1e Seth Mos
			break;
2912 3f383504 smos
		case '6rd':
2913 7a04cd20 Ermal
			interface_6rd_configure($interface, $wancfg);
2914 3f383504 smos
			break;
2915 31c43fd3 smos
		case '6to4':
2916 7a04cd20 Ermal
			interface_6to4_configure($interface, $wancfg);
2917 31c43fd3 smos
			break;
2918 20a7cb15 smos
		case 'track6':
2919 d1878053 Renato Botelho
			interface_track6_configure($interface, $wancfg);
2920 20a7cb15 smos
			break;
2921 5a5413bb Seth Mos
		default:
2922 8103bd1e Seth Mos
			if (is_ipaddr($wancfg['ipaddrv6']) && $wancfg['subnetv6'] <> "") {
2923 5a5413bb Seth Mos
				pfSense_interface_setaddress($realif, "{$wancfg['ipaddrv6']}/{$wancfg['subnetv6']}");
2924 3c5e10fc Seth Mos
				// FIXME: Add IPv6 Support to the pfSense module
2925 5a5413bb Seth Mos
				mwexec("/sbin/ifconfig {$realif} inet6 {$wancfg['ipaddrv6']} prefixlen {$wancfg['subnetv6']} ");
2926
			}
2927
			break;
2928
	}
2929
2930 4a735210 Renato Botelho
	$mtu = get_interface_default_mtu(remove_ifindex($realhwif));
2931 20eb8203 Renato Botelho
	$assignedparent = convert_real_interface_to_friendly_interface_name($realhwif);
2932 08e9c732 Ermal
	if (!empty($assignedparent) && !empty($config['interfaces'][$assignedparent]['mtu']))
2933 20eb8203 Renato Botelho
		$mtu = $config['interfaces'][$assignedparent]['mtu'];
2934 4a735210 Renato Botelho
2935 a976c633 Renato Botelho
	$vlanifs = link_interface_to_vlans($realhwif);
2936
	if (empty($vlanifs))
2937
		$vlanifs = array();
2938
2939 d35233da Ermal
	if (!empty($wancfg['mtu'])) {
2940 7965c38f Ermal
		if (stristr($realif, "_vlan")) {
2941 a1d36777 Renato Botelho
			if (!empty($assignedparent)) {
2942
				$parentmtu = $config['interfaces'][$assignedparent]['mtu'];
2943 d35233da Ermal
				if (empty($parentmtu))
2944 6d1594eb Ermal
					$parentmtu = interface_vlan_mtu_configured($realhwif, $wancfg['mtu']);
2945 2fff3ba2 Ermal
				if ($wancfg['mtu'] > $parentmtu) {
2946 43c6c9af Renato Botelho
					if (get_interface_mtu($realhwif) != $wancfg['mtu'])
2947
						pfSense_interface_mtu($realhwif, $wancfg['mtu']);
2948 2fff3ba2 Ermal
2949
					/* All vlans need to use the same mtu value as their parent. */
2950 a976c633 Renato Botelho
					foreach ($vlanifs as $vlan) {
2951
						if ($vlan['vlanif'] == $realif)
2952
							continue;
2953
						$assignedport = convert_real_interface_to_friendly_interface_name($vlan['vlanif']);
2954
						if (!empty($assignedport)) {
2955
							$portmtu = $config['interfaces'][$assignedport]['mtu'];
2956 43c6c9af Renato Botelho
							if (empty($portmtu) && (get_interface_mtu($vlan['vlanif']) != $wancfg['mtu']))
2957 2fff3ba2 Ermal
								pfSense_interface_mtu($vlan['vlanif'], $wancfg['mtu']);
2958 43c6c9af Renato Botelho
						} else if (get_interface_mtu($vlan['vlanif']) != $wancfg['mtu'])
2959 a976c633 Renato Botelho
							pfSense_interface_mtu($vlan['vlanif'], $wancfg['mtu']);
2960 2fff3ba2 Ermal
					}
2961
				}
2962 4ffa46bf Ermal
			} else {
2963 be2c39b6 Renato Botelho
				/* Parent is not assigned, back to default */
2964
				if (get_interface_mtu($realhwif) != $mtu)
2965
					pfSense_interface_mtu($realhwif, $mtu);
2966
2967
				/* All vlans need to use the same mtu value as their parent. */
2968
				foreach ($vlanifs as $vlan) {
2969
					if ($vlan['vlanif'] == $realif)
2970
						continue;
2971
					$assignedport = convert_real_interface_to_friendly_interface_name($vlan['vlanif']);
2972
					if (!empty($assignedport)) {
2973
						$portmtu = $config['interfaces'][$assignedport]['mtu'];
2974 43c6c9af Renato Botelho
						if (empty($portmtu) && (get_interface_mtu($vlan['vlanif']) != $mtu))
2975 be2c39b6 Renato Botelho
							pfSense_interface_mtu($vlan['vlanif'], $mtu);
2976 43c6c9af Renato Botelho
					} else if (get_interface_mtu($vlan['vlanif']) != $mtu)
2977 be2c39b6 Renato Botelho
						pfSense_interface_mtu($vlan['vlanif'], $mtu);
2978 4ffa46bf Ermal
				}
2979 be2c39b6 Renato Botelho
2980
				if (get_interface_mtu($realif) != $wancfg['mtu'])
2981
					pfSense_interface_mtu($realif, $wancfg['mtu']);
2982 4ffa46bf Ermal
			}
2983 a362a23a Ermal
		} else {
2984 a976c633 Renato Botelho
			foreach ($vlanifs as $vlan) {
2985
				$assignedport = convert_real_interface_to_friendly_interface_name($vlan['vlanif']);
2986 43c6c9af Renato Botelho
				if (empty($assignedport)) {
2987
					if (get_interface_mtu($vlan['vlanif']) != $wancfg['mtu'])
2988
						pfSense_interface_mtu($vlan['vlanif'], $wancfg['mtu']);
2989
				} else {
2990 a976c633 Renato Botelho
					$vlanmtu = $config['interfaces'][$assignedport]['mtu'];
2991 f5c2bf1e Renato Botelho
					if ((empty($vlanmtu) || ($vlanmtu >= $wancfg['mtu'])) && (get_interface_mtu($vlan['vlanif']) != $wancfg['mtu']))
2992 a362a23a Ermal
						pfSense_interface_mtu($vlan['vlanif'], $wancfg['mtu']);
2993
				}
2994
			}
2995 1e08ce64 Ermal
		}
2996
		if ($wancfg['mtu'] != get_interface_mtu($realif))
2997 b1939343 Ermal
			pfSense_interface_mtu($realif, $wancfg['mtu']);
2998 76254caa Renato Botelho
	} else if (stristr($realif, "_vlan")) {
2999 59297ade Ermal
		/* XXX: This is really dangerous for example with vlans changing their parent mtu! */
3000 4ffa46bf Ermal
		$bigmtu = interface_vlan_mtu_configured($realhwif, $mtu);
3001
		if ($mtu < $bigmtu)
3002
			$mtu = $bigmtu;
3003 43c6c9af Renato Botelho
3004
		if (get_interface_mtu($realhwif) != $mtu)
3005
			pfSense_interface_mtu($realhwif, $mtu);
3006 4ffa46bf Ermal
3007
		/* All vlans need to use the same mtu value as their parent. */
3008 a976c633 Renato Botelho
		foreach ($vlanifs as $vlan) {
3009
			if ($vlan['vlanif'] == $realif)
3010
				continue;
3011
			$assignedport = convert_real_interface_to_friendly_interface_name($vlan['vlanif']);
3012
			if (!empty($assignedport)) {
3013
				$portmtu = $config['interfaces'][$assignedport]['mtu'];
3014 43c6c9af Renato Botelho
				if (empty($portmtu) && (get_interface_mtu($vlan['vlanif']) != $mtu))
3015 1dedfdd1 Ermal
					pfSense_interface_mtu($vlan['vlanif'], $mtu);
3016 43c6c9af Renato Botelho
			} else if (get_interface_mtu($vlan['vlanif']) != $mtu)
3017 a976c633 Renato Botelho
				pfSense_interface_mtu($vlan['vlanif'], $mtu);
3018 4ffa46bf Ermal
		}
3019 43c6c9af Renato Botelho
		if (get_interface_mtu($realif) != $mtu)
3020
			pfSense_interface_mtu($realif, $mtu);
3021 3f3252f6 Renato Botelho
	} else {
3022
		/* All vlans need to use the same mtu value as their parent. */
3023
		foreach ($vlanifs as $vlan) {
3024
			$assignedport = convert_real_interface_to_friendly_interface_name($vlan['vlanif']);
3025
			if (!empty($assignedport)) {
3026
				$portmtu = $config['interfaces'][$assignedport]['mtu'];
3027 43c6c9af Renato Botelho
				if (empty($portmtu) && (get_interface_mtu($vlan['vlanif']) != $mtu))
3028 3f3252f6 Renato Botelho
					pfSense_interface_mtu($vlan['vlanif'], $mtu);
3029 43c6c9af Renato Botelho
			} else if (get_interface_mtu($vlan['vlanif']) != $mtu)
3030 3f3252f6 Renato Botelho
				pfSense_interface_mtu($vlan['vlanif'], $mtu);
3031
		}
3032
		if ($mtu != get_interface_mtu($realhwif))
3033
			pfSense_interface_mtu($realhwif, $mtu);
3034
	}
3035 4a735210 Renato Botelho
3036 a976c633 Renato Botelho
	unset($vlanifs);
3037
3038 435f11c8 Ermal Lu?i
	if(does_interface_exist($wancfg['if']))
3039 7284d850 Scott Ullrich
		interfaces_bring_up($wancfg['if']);
3040 67b057a9 Ermal
3041
	interface_netgraph_needed($interface);
3042 be45aa79 Renato Botelho
3043 5b237745 Scott Ullrich
	if (!$g['booting']) {
3044 dcadda55 Ermal
		link_interface_to_vips($interface, "update");
3045 6991dcb1 Ermal
3046 a639bb91 Ermal
		unset($gre);
3047
		$gre = link_interface_to_gre($interface);
3048
		if (!empty($gre))
3049 ed62880b Ermal
			array_walk($gre, 'interface_gre_configure');
3050 a639bb91 Ermal
3051
		unset($gif);
3052
		$gif = link_interface_to_gif($interface);
3053
		if (!empty($gif))
3054 8103bd1e Seth Mos
			array_walk($gif, 'interface_gif_configure');
3055 a639bb91 Ermal
3056 bf17eb72 Ermal
		if ($linkupevent == false || substr($realif, 0, 4) == "ovpn") {
3057 7413cbfd Ermal
			unset($bridgetmp);
3058
			$bridgetmp = link_interface_to_bridge($interface);
3059
			if (!empty($bridgetmp))
3060
				interface_bridge_add_member($bridgetmp, $realif);
3061
		}
3062 ccbd2447 Ermal Luçi
3063 48f23632 Ermal
		$grouptmp = link_interface_to_group($interface);
3064
		if (!empty($grouptmp))
3065 ed62880b Ermal
			array_walk($grouptmp, 'interface_group_add_member');
3066 48f23632 Ermal
3067 a5d6f60b Ermal Lu?i
		if ($interface == "lan")
3068 4476d447 Ermal Luçi
			/* make new hosts file */
3069 ffeb5acf Scott Ullrich
			system_hosts_generate();
3070 4476d447 Ermal Luçi
3071 a5d6f60b Ermal Lu?i
		if ($reloadall == true) {
3072 cfc707f7 Scott Ullrich
3073 a5d6f60b Ermal Lu?i
			/* reconfigure static routes (kernel may have deleted them) */
3074 1ea67f2e Ermal
			system_routing_configure($interface);
3075 cfc707f7 Scott Ullrich
3076 a5d6f60b Ermal Lu?i
			/* reload ipsec tunnels */
3077
			vpn_ipsec_configure();
3078 cfc707f7 Scott Ullrich
3079 b5eeef07 Ermal
			/* restart dnsmasq */
3080
			services_dnsmasq_configure();
3081
3082 a5d6f60b Ermal Lu?i
			/* update dyndns */
3083 422bc2a7 Ermal
			send_event("service reload dyndns {$interface}");
3084 a23d7248 Scott Ullrich
3085 a5d6f60b Ermal Lu?i
			/* reload captive portal */
3086 769e254e Ermal
			captiveportal_init_rules();
3087 a5d6f60b Ermal Lu?i
		}
3088 5b237745 Scott Ullrich
	}
3089 cfc707f7 Scott Ullrich
3090 5b237745 Scott Ullrich
	return 0;
3091
}
3092
3093 7a04cd20 Ermal
function interface_track6_configure($interface = "lan", $wancfg) {
3094 20a7cb15 smos
	global $config, $g;
3095
3096 7a04cd20 Ermal
	if (!is_array($wancfg))
3097
		return;
3098
3099
	if (!isset($wancfg['enable']))
3100 b0059636 Ermal
		return;
3101 be45aa79 Renato Botelho
3102 20a7cb15 smos
	/* If the interface is not configured via another, exit */
3103 b0059636 Ermal
	if (empty($wancfg['track6-interface']))
3104
		return;
3105 20a7cb15 smos
3106 e90c833a smos
	/* always configure a link-local of fe80::1:1 on the track6 interfaces */
3107
	$realif = get_real_interface($interface);
3108
	mwexec("/sbin/ifconfig {$realif} inet6 fe80::1:1%{$realif}");
3109
3110 7a04cd20 Ermal
	$trackcfg = $config['interfaces'][$wancfg['track6-interface']];
3111
	if (!isset($trackcfg['enable'])) {
3112
		log_error("Interface {$interface} tracking non-existant interface {$wancfg['track6-interface']}");
3113
		return;
3114
	}
3115
3116
	switch($trackcfg['ipaddrv6']) {
3117 6fb66736 Ermal
	case "6to4":
3118
		if ($g['debug'])
3119
			log_error("Interface {$interface} configured via {$wancfg['track6-interface']}  type {$type}");
3120
		interface_track6_6to4_configure($interface, $wancfg);
3121
		break;
3122
	case "6rd":
3123
		if ($g['debug'])
3124
			log_error("Interface {$interface} configured via {$wancfg['track6-interface']}  type {$type}");
3125
		interface_track6_6rd_configure($interface, $wancfg);
3126
		break;
3127
	case "dhcp6":
3128
		if ($g['debug'])
3129
			log_error("Interface {$interface} configured via {$wancfg['track6-interface']}  type {$type}");
3130
		interface_track6_dhcp6_configure($interface, $wancfg);
3131
		break;
3132 20a7cb15 smos
	}
3133 b0059636 Ermal
3134 7fd67662 Ermal
	if (!$g['booting']) {
3135
		if (!function_exists('services_dhcpd_configure'))
3136
			require_once("services.inc");
3137 6387590f Ermal
3138 7fd67662 Ermal
		services_dhcpd_configure("inet6");
3139
	}
3140 6387590f Ermal
3141 20a7cb15 smos
	return 0;
3142
}
3143
3144 7a04cd20 Ermal
function interface_track6_6rd_configure($interface = "lan", $lancfg) {
3145 20a7cb15 smos
	global $config, $g;
3146 da9dd1b4 Ermal
	global $interface_ipv6_arr_cache;
3147
        global $interface_snv6_arr_cache;
3148 20a7cb15 smos
3149 7a04cd20 Ermal
	if (!is_array($lancfg))
3150 b0059636 Ermal
		return;
3151 be45aa79 Renato Botelho
3152 20a7cb15 smos
	/* If the interface is not configured via another, exit */
3153 b0059636 Ermal
	if (empty($lancfg['track6-interface']))
3154
		return;
3155
3156
	if (!is_numeric($lancfg['track6-prefix-id']))
3157 20a7cb15 smos
		$lancfg['track6-prefix-id'] = 0;
3158 be45aa79 Renato Botelho
3159 20a7cb15 smos
	$wancfg = $config['interfaces'][$lancfg['track6-interface']];
3160 7a04cd20 Ermal
	if (empty($wancfg)) {
3161
		log_error("Interface {$interface} tracking non-existant interface {$lancfg['track6-interface']}");
3162 b0059636 Ermal
		return;
3163 7a04cd20 Ermal
	}
3164 be45aa79 Renato Botelho
3165 ff5674dc Ermal
	$ip4address = get_interface_ip($lancfg['track6-interface']);
3166 7a04cd20 Ermal
	if (!is_ipaddrv4($ip4address)) { /* XXX: This should not be needed by 6rd || (is_private_ip($ip4address))) { */
3167 ff5674dc Ermal
		log_error("The interface IPv4 '{$ip4address}' address on interface '{$lancfg['track6-interface']}' is not public, not configuring 6RD tunnel");
3168 b0059636 Ermal
		return;
3169 20a7cb15 smos
	}
3170
	$hexwanv4 = return_hex_ipv4($ip4address);
3171 be45aa79 Renato Botelho
3172 20a7cb15 smos
	/* create the long prefix notation for math, save the prefix length */
3173
	$rd6prefix = explode("/", $wancfg['prefix-6rd']);
3174
	$rd6prefixlen = $rd6prefix[1];
3175
	$rd6prefix = Net_IPv6::uncompress($rd6prefix[0]);
3176
3177
	/* binary presentation of the prefix for all 128 bits. */
3178
	$rd6lanbin = convert_ipv6_to_128bit($rd6prefix);
3179 be45aa79 Renato Botelho
3180 20a7cb15 smos
	/* just save the left prefix length bits */
3181
	$rd6lanbin = substr($rd6lanbin, 0, $rd6prefixlen);
3182
	/* add the v4 address, offset n bits from the left */
3183
	$rd6lanbin .= substr(sprintf("%032b", hexdec($hexwanv4)), (0 + $wancfg['prefix-6rd-v4plen']), 32);
3184
3185
	/* add the custom prefix id, max 32bits long? (64 bits - (prefixlen + (32 - v4plen)) */
3186
	/* 64 - (37 + (32 - 17)) = 8 == /52 */
3187
	$restbits = 64 - ($rd6prefixlen + (32 - $wancfg['prefix-6rd-v4plen']));
3188
	// echo "64 - (prefixlen {$rd6prefixlen} + v4len (32 - {$wancfg['prefix-6rd-v4plen']})) = {$restbits} \n";
3189
	$rd6lanbin .= substr(sprintf("%032b", str_pad($lancfg['track6-prefix-id'], 32, "0", STR_PAD_LEFT)), (32 - $restbits), 32);
3190
	/* fill the rest out with zeros */
3191
	$rd6lanbin = str_pad($rd6lanbin, 128, "0", STR_PAD_RIGHT);;
3192
3193 be45aa79 Renato Botelho
	/* convert the 128 bits for the lan address back into a valid IPv6 address */
3194 20a7cb15 smos
	$rd6lan = convert_128bit_to_ipv6($rd6lanbin) ."1";
3195 be45aa79 Renato Botelho
3196 b0059636 Ermal
	$lanif = get_real_interface($interface);
3197 c4fc2eae Ermal
	$oip = find_interface_ipv6($lanif);
3198
	if (is_ipaddrv6($oip))
3199
		mwexec("/sbin/ifconfig {$lanif} inet6 {$oip} delete");
3200 da9dd1b4 Ermal
	unset($interface_ipv6_arr_cache[$lanif]);
3201
	unset($interface_snv6_arr_cache[$lanif]);
3202 20a7cb15 smos
	log_error("rd6 {$interface} with ipv6 address {$rd6lan} based on {$lancfg['track6-interface']} ipv4 {$ip4address}");
3203
	mwexec("/sbin/ifconfig {$lanif} inet6 {$rd6lan} prefixlen 64");
3204 b0059636 Ermal
3205 20a7cb15 smos
	return 0;
3206
}
3207
3208 7a04cd20 Ermal
function interface_track6_6to4_configure($interface = "lan", $lancfg) {
3209 20a7cb15 smos
	global $config, $g;
3210 da9dd1b4 Ermal
	global $interface_ipv6_arr_cache;
3211
        global $interface_snv6_arr_cache;
3212 20a7cb15 smos
3213 7a04cd20 Ermal
	if (!is_array($lancfg))
3214 b0059636 Ermal
		return;
3215 be45aa79 Renato Botelho
3216 20a7cb15 smos
	/* If the interface is not configured via another, exit */
3217 b0059636 Ermal
	if (empty($lancfg['track6-interface']))
3218
		return;
3219
3220 7a04cd20 Ermal
	$wancfg = $config['interfaces'][$lancfg['track6-interface']];
3221
	if (empty($wancfg)) {
3222
		log_error("Interface {$interface} tracking non-existant interface {$lancfg['track6-interface']}");
3223
		return;
3224
	}
3225
3226 b0059636 Ermal
	if (!is_numeric($lancfg['track6-prefix-id']))
3227 20a7cb15 smos
		$lancfg['track6-prefix-id'] = 0;
3228 be45aa79 Renato Botelho
3229 ff5674dc Ermal
	$ip4address = get_interface_ip($lancfg['track6-interface']);
3230 b0059636 Ermal
	if (!is_ipaddrv4($ip4address) || is_private_ip($ip4address)) {
3231 ff5674dc Ermal
		log_error("The interface IPv4 '{$ip4address}' address on interface '{$lancfg['track6-interface']}' is not public, not configuring 6RD tunnel");
3232 b0059636 Ermal
		return;
3233 20a7cb15 smos
	}
3234
	$hexwanv4 = return_hex_ipv4($ip4address);
3235 be45aa79 Renato Botelho
3236 20a7cb15 smos
	/* create the long prefix notation for math, save the prefix length */
3237
	$sixto4prefix = "2002::";
3238
	$sixto4prefixlen = 16;
3239
	$sixto4prefix = Net_IPv6::uncompress($sixto4prefix);
3240
3241
	/* binary presentation of the prefix for all 128 bits. */
3242
	$sixto4lanbin = convert_ipv6_to_128bit($sixto4prefix);
3243 be45aa79 Renato Botelho
3244 20a7cb15 smos
	/* just save the left prefix length bits */
3245
	$sixto4lanbin = substr($sixto4lanbin, 0, $sixto4prefixlen);
3246
	/* add the v4 address */
3247
	$sixto4lanbin .= sprintf("%032b", hexdec($hexwanv4));
3248
	/* add the custom prefix id */
3249
	$sixto4lanbin .= sprintf("%016b", $lancfg['track6-prefix-id']);
3250
	/* fill the rest out with zeros */
3251
	$sixto4lanbin = str_pad($sixto4lanbin, 128, "0", STR_PAD_RIGHT);;
3252 be45aa79 Renato Botelho
3253
	/* convert the 128 bits for the lan address back into a valid IPv6 address */
3254 20a7cb15 smos
	$sixto4lan = convert_128bit_to_ipv6($sixto4lanbin) ."1";
3255 be45aa79 Renato Botelho
3256 b0059636 Ermal
	$lanif = get_real_interface($interface);
3257 c4fc2eae Ermal
	$oip = find_interface_ipv6($lanif);
3258
	if (is_ipaddrv6($oip))
3259
		mwexec("/sbin/ifconfig {$lanif} inet6 {$oip} delete");
3260 da9dd1b4 Ermal
	unset($interface_ipv6_arr_cache[$lanif]);
3261
	unset($interface_snv6_arr_cache[$lanif]);
3262 20a7cb15 smos
	log_error("sixto4 {$interface} with ipv6 address {$sixto4lan} based on {$lancfg['track6-interface']} ipv4 {$ip4address}");
3263
	mwexec("/sbin/ifconfig {$lanif} inet6 {$sixto4lan} prefixlen 64");
3264 b0059636 Ermal
3265 20a7cb15 smos
	return 0;
3266
}
3267
3268 7a41d737 Ermal
function interface_track6_dhcp6_configure($interface = "lan", $lancfg) {
3269
	global $config, $g;
3270 da9dd1b4 Ermal
	global $interface_ipv6_arr_cache;
3271
        global $interface_snv6_arr_cache;
3272 7a41d737 Ermal
3273
	if (!is_array($lancfg))
3274
		return;
3275
3276
	/* If the interface is not configured via another, exit */
3277
	if (empty($lancfg['track6-interface']))
3278
		return;
3279
3280
	if (!is_numeric($lancfg['track6-prefix-id']))
3281
		$lancfg['track6-prefix-id'] = 0;
3282
3283
	$wancfg = $config['interfaces'][$lancfg['track6-interface']];
3284
	if (empty($wancfg)) {
3285
		log_error("Interface {$interface} tracking non-existant interface {$lancfg['track6-interface']}");
3286
		return;
3287
	}
3288
3289 1fadb9d1 Ermal
	$lanif = get_real_interface($interface);
3290
	$oip = find_interface_ipv6($lanif);
3291
	if (is_ipaddrv6($oip))
3292
		mwexec("/sbin/ifconfig {$lanif} inet6 {$oip} delete");
3293 da9dd1b4 Ermal
	unset($interface_ipv6_arr_cache[$lanif]);
3294
	unset($interface_snv6_arr_cache[$lanif]);
3295 1fadb9d1 Ermal
3296 e082d2f4 Ermal
	if ($wancfg['ipaddrv6'] == "slaac") {
3297 ff5674dc Ermal
		$ifcfgipv6 = get_interface_ipv6($lancfg['track6-interface']);
3298 e082d2f4 Ermal
		if (is_ipaddrv6($ifcfgipv6)) {
3299
			$dhcp6lanarr = explode(":", Net_IPv6::uncompress($ifcfgipv6));
3300
			$dhcp6lanarr[4] = 0;
3301
			$dhcp6lanarr[5] = 0;
3302
			$dhcp6lanarr[6] = 0;
3303
			$dhcp6lanarr[7] = 1;
3304
			$dhcp6lan =  Net_IPv6::compress(implode(":", $dhcp6lanarr));
3305
			log_error("dhcp6 {$interface} with ipv6 address {$dhcp6lan} based on {$lancfg['track6-interface']}");
3306
			mwexec("/sbin/ifconfig {$lanif} inet6 {$dhcp6lan} prefixlen 64");
3307
		}
3308
	}
3309
3310 7a41d737 Ermal
	return 0;
3311
}
3312
3313 7a04cd20 Ermal
function interface_6rd_configure($interface = "wan", $wancfg) {
3314 668e8961 smos
	global $config, $g;
3315
3316 be45aa79 Renato Botelho
	/* because this is a tunnel interface we can only function
3317 668e8961 smos
	 *	with a public IPv4 address on the interface */
3318
3319 7a04cd20 Ermal
	if (!is_array($wancfg))
3320 b0059636 Ermal
		return;
3321 668e8961 smos
3322
	$wanif = get_real_interface($interface);
3323
	$ip4address = find_interface_ip($wanif);
3324 b0059636 Ermal
	if ((!is_ipaddrv4($ip4address)) || (is_private_ip($ip4address))) {
3325 668e8961 smos
		log_error("The interface IPv4 '{$ip4address}' address on interface '{$wanif}' is not public, not configuring 6RD tunnel");
3326 1f78ab3a smos
		return false;
3327 668e8961 smos
	}
3328 20a7cb15 smos
	$hexwanv4 = return_hex_ipv4($ip4address);
3329 be45aa79 Renato Botelho
3330 b0059636 Ermal
	if (!is_numeric($wancfg['prefix-6rd-v4plen']))
3331 20a7cb15 smos
		$wancfg['prefix-6rd-v4plen'] = 0;
3332 668e8961 smos
3333 51c57aae smos
	/* create the long prefix notation for math, save the prefix length */
3334 f87ccbed smos
	$rd6prefix = explode("/", $wancfg['prefix-6rd']);
3335
	$rd6prefixlen = $rd6prefix[1];
3336
	$rd6prefix = Net_IPv6::uncompress($rd6prefix[0]);
3337 51c57aae smos
3338
	/* we need the hex form of the broker IPv4 address */
3339 20a7cb15 smos
	$hexbrv4 = return_hex_ipv4($wancfg['gateway-6rd']);
3340 be45aa79 Renato Botelho
3341 51c57aae smos
	/* binary presentation of the prefix for all 128 bits. */
3342 20a7cb15 smos
	$rd6prefixbin = convert_ipv6_to_128bit($rd6prefix);
3343 be45aa79 Renato Botelho
3344 4aa569bd smos
	/* just save the left prefix length bits */
3345
	$rd6brprefixbin = substr($rd6prefixbin, 0, $rd6prefixlen);
3346
	/* if the prefix length is not 32 bits we need to shave bits off from the left of the v4 address. */
3347
	$rd6brprefixbin .= substr(sprintf("%032b", hexdec($hexbrv4)), $wancfg['prefix-6rd-v4plen'], 32);
3348
	/* fill out the rest with 0's */
3349 dcddb2fa Ermal
	$rd6brprefixbin = str_pad($rd6brprefixbin, 128, "0", STR_PAD_RIGHT);
3350 4aa569bd smos
3351 be45aa79 Renato Botelho
	/* convert the 128 bits for the broker address back into a valid IPv6 address */
3352 4aa569bd smos
	$rd6brgw = convert_128bit_to_ipv6($rd6brprefixbin);
3353
3354 51c57aae smos
	/* just save the left prefix length bits */
3355 20a7cb15 smos
	$rd6prefixbin = substr($rd6prefixbin, 0, $rd6prefixlen);
3356 51c57aae smos
	/* if the prefix length is not 32 bits we need to shave bits off from the left of the v4 address. */
3357 4aa569bd smos
	$rd6prefixbin .= substr(sprintf("%032b", hexdec($hexwanv4)), $wancfg['prefix-6rd-v4plen'], 32);
3358 20a7cb15 smos
	/* fill out the rest with 0's */
3359
	$rd6prefixbin = str_pad($rd6prefixbin, 128, "0", STR_PAD_RIGHT);;
3360 51c57aae smos
3361 be45aa79 Renato Botelho
	/* convert the 128 bits for the broker address back into a valid IPv6 address */
3362 4aa569bd smos
	$rd6prefix = convert_128bit_to_ipv6($rd6prefixbin);
3363 f87ccbed smos
3364 7d1f2eac Ermal
	/* XXX: need to extend to support variable prefix size for v4 */
3365 b686e5d0 Ermal
	if (!is_module_loaded("if_stf"))
3366
		mwexec("/sbin/kldload if_stf.ko");
3367 7d1f2eac Ermal
	$stfiface = "{$interface}_stf";
3368 c4fc2eae Ermal
	if (does_interface_exist($stfiface))
3369
		pfSense_interface_destroy($stfiface);
3370
	$tmpstfiface = pfSense_interface_create("stf");
3371
	pfSense_interface_rename($tmpstfiface, $stfiface);
3372 7d1f2eac Ermal
	pfSense_interface_flags($stfiface, IFF_LINK2);
3373
	mwexec("/sbin/ifconfig {$stfiface} inet6 {$rd6prefix}/{$rd6prefixlen}");
3374 b0059636 Ermal
	if ($g['debug'])
3375 7d1f2eac Ermal
		log_error("Created 6rd interface {$stfiface} {$rd6prefix}/{$rd6prefixlen}");
3376 668e8961 smos
3377 f55b6cbb smos
	/* write out a default router file */
3378 20a7cb15 smos
	file_put_contents("{$g['tmp_path']}/{$wanif}_routerv6", "{$rd6brgw}\n");
3379
	file_put_contents("{$g['tmp_path']}/{$wanif}_defaultgwv6", "{$rd6brgw}\n");
3380 2d5ca06e smos
3381 5ee79d32 Ermal
	$ip4gateway = get_interface_gateway($interface);
3382 66c73aab Ermal
	if (is_ipaddrv4($ip4gateway))
3383 b0059636 Ermal
		mwexec("/sbin/route change -host " . $wancfg['gateway-6rd'] . " {$ip4gateway}");
3384 c8ed8142 smos
3385 2d5ca06e smos
	/* configure dependent interfaces */
3386 7a04cd20 Ermal
	if (!$g['booting'])
3387
		link_interface_to_track6($interface, "update");
3388 66c73aab Ermal
3389 f55b6cbb smos
	return 0;
3390 668e8961 smos
}
3391
3392 7a04cd20 Ermal
function interface_6to4_configure($interface = "wan", $wancfg){
3393 31c43fd3 smos
	global $config, $g;
3394
3395 be45aa79 Renato Botelho
	/* because this is a tunnel interface we can only function
3396 31c43fd3 smos
	 *	with a public IPv4 address on the interface */
3397
3398 7a04cd20 Ermal
	if (!is_array($wancfg))
3399
		return;
3400 31c43fd3 smos
3401
	$wanif = get_real_interface($interface);
3402
	$ip4address = find_interface_ip($wanif);
3403
	if((!is_ipaddrv4($ip4address)) || (is_private_ip($ip4address))) {
3404
		log_error("The interface IPv4 '{$ip4address}' address on interface '{$wanif}' is not public, not configuring 6RD tunnel");
3405
		return false;
3406
	}
3407 be45aa79 Renato Botelho
3408 31c43fd3 smos
	/* create the long prefix notation for math, save the prefix length */
3409
	$stfprefixlen = 16;
3410
	$stfprefix = Net_IPv6::uncompress("2002::");
3411
	$stfarr = explode(":", $stfprefix);
3412
	$v4prefixlen = "0";
3413 be45aa79 Renato Botelho
3414 31c43fd3 smos
	/* we need the hex form of the interface IPv4 address */
3415
	$ip4arr = explode(".", $ip4address);
3416
	$hexwanv4 = "";
3417
	foreach($ip4arr as $octet)
3418
		$hexwanv4 .= sprintf("%02x", $octet);
3419
3420
	/* we need the hex form of the broker IPv4 address */
3421
	$ip4arr = explode(".", "192.88.99.1");
3422
	$hexbrv4 = "";
3423
	foreach($ip4arr as $octet)
3424
		$hexbrv4 .= sprintf("%02x", $octet);
3425 be45aa79 Renato Botelho
3426 31c43fd3 smos
	/* binary presentation of the prefix for all 128 bits. */
3427
	$stfprefixbin = "";
3428
	foreach($stfarr as $element) {
3429
		$stfprefixbin .= sprintf("%016b", hexdec($element));
3430
	}
3431
	/* just save the left prefix length bits */
3432
	$stfprefixstartbin = substr($stfprefixbin, 0, $stfprefixlen);
3433
3434
	/* if the prefix length is not 32 bits we need to shave bits off from the left of the v4 address. */
3435
	$stfbrokerbin = substr(sprintf("%032b", hexdec($hexbrv4)), $v4prefixlen, 32);
3436
	$stfbrokerbin = str_pad($stfprefixstartbin . $stfbrokerbin, 128, "0", STR_PAD_RIGHT);;
3437
3438
	/* for the local subnet too. */
3439
	$stflanbin = substr(sprintf("%032b", hexdec($hexwanv4)), $v4prefixlen, 32);
3440
	$stflanbin = str_pad($stfprefixstartbin . $stflanbin, 128, "0", STR_PAD_RIGHT);;
3441
3442 be45aa79 Renato Botelho
	/* convert the 128 bits for the broker address back into a valid IPv6 address */
3443 31c43fd3 smos
	$stfbrarr = array();
3444
	$stfbrbinarr = array();
3445
	$stfbrbinarr = str_split($stfbrokerbin, 16);
3446
	foreach($stfbrbinarr as $bin)
3447
		$stfbrarr[] = dechex(bindec($bin));
3448
	$stfbrgw = Net_IPv6::compress(implode(":", $stfbrarr));
3449
3450 be45aa79 Renato Botelho
	/* convert the 128 bits for the broker address back into a valid IPv6 address */
3451 31c43fd3 smos
	$stflanarr = array();
3452
	$stflanbinarr = array();
3453
	$stflanbinarr = str_split($stflanbin, 16);
3454
	foreach($stflanbinarr as $bin)
3455
		$stflanarr[] = dechex(bindec($bin));
3456
	$stflanpr = Net_IPv6::compress(implode(":", $stflanarr));
3457
	$stflanarr[7] = 1;
3458
	$stflan = Net_IPv6::compress(implode(":", $stflanarr));
3459
3460
	/* setup the stf interface */
3461 b686e5d0 Ermal
	if (!is_module_loaded("if_stf"))
3462
		mwexec("/sbin/kldload if_stf.ko");
3463 7d1f2eac Ermal
	$stfiface = "{$interface}_stf";
3464 c4fc2eae Ermal
	if (does_interface_exist($stfiface))
3465
		pfSense_interface_destroy($stfiface);
3466
	$tmpstfiface = pfSense_interface_create("stf");
3467
	pfSense_interface_rename($tmpstfiface, $stfiface);
3468 7d1f2eac Ermal
	pfSense_interface_flags($stfiface, IFF_LINK2);
3469
	mwexec("/sbin/ifconfig {$stfiface} inet6 {$stflanpr} prefixlen 16");
3470 31c43fd3 smos
3471 7d1f2eac Ermal
	if ($g['debug'])
3472
		log_error("Set IPv6 address inet6 {$stflanpr} prefixlen 16 for {$stfiface}, route {$stfbrgw}");
3473 be45aa79 Renato Botelho
3474 31c43fd3 smos
	/* write out a default router file */
3475
	file_put_contents("{$g['tmp_path']}/{$wanif}_routerv6", "{$stfbrgw}");
3476
	file_put_contents("{$g['tmp_path']}/{$wanif}_defaultgwv6", "{$stfbrgw}");
3477 2d5ca06e smos
3478 5ee79d32 Ermal
	$ip4gateway = get_interface_gateway($interface);
3479
	if (is_ipaddrv4($ip4gateway))
3480 c8ed8142 smos
		mwexec("route change -host 192.88.99.1 {$ip4gateway}");
3481
3482 7a04cd20 Ermal
	if (!$g['booting'])
3483
		link_interface_to_track6($interface, "update");
3484 be45aa79 Renato Botelho
3485 31c43fd3 smos
	return 0;
3486
}
3487
3488 7a04cd20 Ermal
function interface_dhcpv6_configure($interface = "wan", $wancfg) {
3489 ed395640 Seth Mos
	global $config, $g;
3490
3491 7a04cd20 Ermal
	if (!is_array($wancfg))
3492 b0059636 Ermal
		return;
3493 ed395640 Seth Mos
3494
	$wanif = get_real_interface($interface);
3495 d53a9a51 smos
	$dhcp6cconf = "";
3496
	$dhcp6cconf .= "interface {$wanif} {\n";
3497 feb88a14 smos
3498 d53a9a51 smos
	/* for SLAAC interfaces we do fire off a dhcp6 client for just our name servers */
3499
	if($wancfg['ipaddrv6'] == "slaac") {
3500
		$dhcp6cconf .= "	information-only;\n";
3501
		$dhcp6cconf .= "	request domain-name-servers;\n";
3502
		$dhcp6cconf .= "	request domain-name;\n";
3503
		$dhcp6cconf .= "	script \"{$g['varetc_path']}/dhcp6c_{$interface}_script.sh\"; # we'd like some nameservers please\n";
3504
		$dhcp6cconf .= "};\n";
3505
	} else {
3506 be45aa79 Renato Botelho
3507 d53a9a51 smos
		$dhcp6cconf .= " 	send ia-na 0;	# request stateful address\n";
3508 b0059636 Ermal
		if(is_numeric($wancfg['dhcp6-ia-pd-len']))
3509 d53a9a51 smos
			$dhcp6cconf .= "	send ia-pd 0;	# request prefix delegation\n";
3510
		$dhcp6cconf .= "request domain-name-servers;\n";
3511
		$dhcp6cconf .= "request domain-name;\n";
3512
		$dhcp6cconf .= "script \"{$g['varetc_path']}/dhcp6c_{$interface}_script.sh\"; # we'd like some nameservers please\n";
3513
3514
		$dhcp6cconf .= "};\n";
3515
		$dhcp6cconf .= "id-assoc na 0 { };\n";
3516
		if(is_numeric($wancfg['dhcp6-ia-pd-len'])) {
3517
			/* Setup the prefix delegation */
3518
			$dhcp6cconf .= "id-assoc pd 0 {\n";
3519 7a04cd20 Ermal
			$iflist = link_interface_to_track6($interface);
3520
			foreach ($iflist as $friendly => $ifcfg) {
3521
				if (is_numeric($ifcfg['track6-prefix-id'])) {
3522
					if ($g['debug'])
3523
						log_error("setting up $ifdescr - {$ifcfg['track6-prefix-id']}");
3524 d53a9a51 smos
					$realif = get_real_interface($friendly);
3525
					$dhcp6cconf .= "	prefix-interface {$realif} {\n";
3526 7a04cd20 Ermal
					$dhcp6cconf .= "		sla-id {$ifcfg['track6-prefix-id']};\n";
3527 d53a9a51 smos
					$dhcp6cconf .= "		sla-len {$wancfg['dhcp6-ia-pd-len']};\n";
3528
					$dhcp6cconf .= "	};\n";
3529
				}
3530
			}
3531 7a04cd20 Ermal
			unset($iflist, $ifcfg);
3532 d53a9a51 smos
			$dhcp6cconf .= "};\n";
3533
		}
3534
	}
3535 b0059636 Ermal
	/* wide-dhcp6c works for now. */
3536
	if (!@file_put_contents("{$g['varetc_path']}/dhcp6c_{$interface}.conf", $dhcp6cconf)) {
3537
		printf("Error: cannot open dhcp6c_{$interface}.conf in interface_dhcpv6_configure() for writing.\n");
3538 d12ae241 Renato Botelho
		unset($dhcp6cconf);
3539 b0059636 Ermal
		return 1;
3540
	}
3541 d12ae241 Renato Botelho
	unset($dhcp6cconf);
3542 ed395640 Seth Mos
3543 b0059636 Ermal
	$dhcp6cscript = "#!/bin/sh\n";
3544
	$dhcp6cscript .= "# This shell script launches /etc/rc.newwanipv6 with a interface argument.\n";
3545
	$dhcp6cscript .= "/etc/rc.newwanipv6 {$wanif} \n";
3546 d53a9a51 smos
	/* Add wide-dhcp6c shell script here. Because we can not pass a argument to it. */
3547 b0059636 Ermal
	if (!@file_put_contents("{$g['varetc_path']}/dhcp6c_{$interface}_script.sh", $dhcp6cscript)) {
3548 d53a9a51 smos
		printf("Error: cannot open dhcp6c_{$interface}_script.sh in interface_dhcpv6_configure() for writing.\n");
3549 d12ae241 Renato Botelho
		unset($dhcp6cscript);
3550 d53a9a51 smos
		return 1;
3551
	}
3552 d12ae241 Renato Botelho
	unset($dhcp6cscript);
3553 b0059636 Ermal
	@chmod("{$g['varetc_path']}/dhcp6c_{$interface}_script.sh", 0755);
3554 d53a9a51 smos
3555 29f2f07a Ermal
	$rtsoldscript = "#!/bin/sh\n";
3556
	$rtsoldscript .= "# This shell script launches dhcp6c and configured gateways for this interface.\n";
3557
	$rtsoldscript .= "echo $2 > {$g['tmp_path']}/{$wanif}_routerv6\n";
3558
	$rtsoldscript .= "echo $2 > {$g['tmp_path']}/{$wanif}_defaultgwv6\n";
3559
	$rtsoldscript .= "if [ -f {$g['varrun_path']}/dhcp6c_{$wanif}.pid ]; then\n";
3560
	$rtsoldscript .= "\tpkill -F {$g['varrun_path']}/dhcp6c_{$wanif}.pid\n";
3561
	$rtsoldscript .= "fi\n";
3562
	$rtsoldscript .= "/usr/local/sbin/dhcp6c -d -c {$g['varetc_path']}/dhcp6c_{$interface}.conf -p {$g['varrun_path']}/dhcp6c_{$wanif}.pid {$wanif}\n";
3563
	/* Add wide-dhcp6c shell script here. Because we can not pass a argument to it. */
3564
	if (!@file_put_contents("{$g['varetc_path']}/rtsold_{$wanif}_script.sh", $rtsoldscript)) {
3565
		printf("Error: cannot open rtsold_{$interface}_script.sh in interface_dhcpv6_configure() for writing.\n");
3566
		unset($rtsoldscript);
3567
		return 1;
3568
	}
3569
	unset($rtsoldscript);
3570
	@chmod("{$g['varetc_path']}/rtsold_{$wanif}_script.sh", 0755);
3571 d53a9a51 smos
3572 c65d3051 Seth Mos
	/* accept router advertisements for this interface */
3573 ef851fed smos
	mwexec("/sbin/sysctl -w net.inet6.ip6.accept_rtadv=1");
3574 49047fb4 smos
	log_error("Accept router advertisements on interface {$wanif} ");
3575 100c7be0 Seth Mos
	mwexec("/sbin/ifconfig {$wanif} inet6 accept_rtadv");
3576 61c4383d smos
3577 29f2f07a Ermal
	/* fire up rtsold for IPv6 RAs first, this backgrounds immediately. It will call dhcp6c */
3578
	if (isvalidpid("{$g['varrun_path']}/rtsold_{$wanif}.pid"))
3579
		killbypid("{$g['varrun_path']}/rtsold_{$wanif}.pid");
3580
	mwexec("/usr/sbin/rtsold -m -p {$g['varrun_path']}/rtsold_{$wanif}.pid -O {$g['varetc_path']}/rtsold_{$wanif}_script.sh {$wanif}");
3581 82769dfe smos
3582 29f2f07a Ermal
	/* NOTE: will be called from rtsold invoked script 
3583
	 * link_interface_to_track6($interface, "update");
3584
	 */
3585 b0059636 Ermal
3586 ed395640 Seth Mos
	return 0;
3587
}
3588
3589 8103bd1e Seth Mos
function interface_dhcp_configure($interface = "wan") {
3590 ed395640 Seth Mos
	global $config, $g;
3591
3592
	$wancfg = $config['interfaces'][$interface];
3593
	$wanif = $wancfg['if'];
3594 df9e93f0 Ermal
	if (empty($wancfg))
3595
		$wancfg = array();
3596 5b237745 Scott Ullrich
3597 0311dbd5 Scott Ullrich
	/* generate dhclient_wan.conf */
3598 67ee1ec5 Ermal Luçi
	$fd = fopen("{$g['varetc_path']}/dhclient_{$interface}.conf", "w");
3599 5b237745 Scott Ullrich
	if (!$fd) {
3600 905ea336 Phil Davis
		printf(printf(gettext("Error: cannot open dhclient_%s.conf in interface_dhcp_configure() for writing.%s"), $interface, "\n"));
3601 5b237745 Scott Ullrich
		return 1;
3602
	}
3603 eb772abd Scott Ullrich
3604 2305d4c5 Scott Ullrich
	if ($wancfg['dhcphostname']) {
3605
		$dhclientconf_hostname = "send dhcp-client-identifier \"{$wancfg['dhcphostname']}\";\n";
3606
		$dhclientconf_hostname .= "\tsend host-name \"{$wancfg['dhcphostname']}\";\n";
3607
	} else {
3608
		$dhclientconf_hostname = "";
3609
	}
3610
3611 85a5da13 Ermal Luçi
	$wanif = get_real_interface($interface);
3612 df9e93f0 Ermal
	if (empty($wanif)) {
3613 07e40c1f Carlos Eduardo Ramos
		log_error(sprintf(gettext("Invalid interface \"%s\" in interface_dhcp_configure()"), $interface));
3614 c1cc447c gnhb
		return 0;
3615 3a906378 gnhb
	}
3616 1c3ddd9e Renato Botelho
	$dhclientconf = "";
3617 be45aa79 Renato Botelho
3618 6d76590c Scott Ullrich
	$dhclientconf .= <<<EOD
3619 67ee1ec5 Ermal Luçi
interface "{$wanif}" {
3620 76d3b9a3 Chris Buechler
timeout 60;
3621 88810240 smos
retry 15;
3622 ce69a638 Scott Ullrich
select-timeout 0;
3623
initial-interval 1;
3624 2305d4c5 Scott Ullrich
	{$dhclientconf_hostname}
3625
	script "/sbin/dhclient-script";
3626 5b237745 Scott Ullrich
}
3627
3628
EOD;
3629
3630 bc40d758 Seth Mos
if(is_ipaddr($wancfg['alias-address'])) {
3631
	$subnetmask = gen_subnet_mask($wancfg['alias-subnet']);
3632
	$dhclientconf .= <<<EOD
3633
alias {
3634 67ee1ec5 Ermal Luçi
	interface  "{$wanif}";
3635 bc40d758 Seth Mos
	fixed-address {$wancfg['alias-address']};
3636
	option subnet-mask {$subnetmask};
3637
}
3638
3639
EOD;
3640
}
3641 5b237745 Scott Ullrich
	fwrite($fd, $dhclientconf);
3642
	fclose($fd);
3643 eb772abd Scott Ullrich
3644 d7147b1c Scott Ullrich
	/* bring wan interface up before starting dhclient */
3645 3a906378 gnhb
	if($wanif)
3646
		interfaces_bring_up($wanif);
3647 be45aa79 Renato Botelho
	else
3648 07e40c1f Carlos Eduardo Ramos
		log_error(printf(gettext("Could not bring up %s interface in interface_dhcp_configure()"), $wanif));
3649 eacc8c14 Scott Ullrich
3650 deb39cf2 Ermal
	$pid = find_dhclient_process($wanif);
3651
	if ($pid)
3652
		posix_kill($pid, SIGTERM);
3653 7149c4e7 Seth Mos
	/* fire up dhclient */
3654 15d15c7f bcyrill
	mwexec("/sbin/dhclient -c {$g['varetc_path']}/dhclient_{$interface}.conf {$wanif} > {$g['tmp_path']}/{$wanif}_output 2> {$g['tmp_path']}/{$wanif}_error_output");
3655 0119d2f7 Scott Ullrich
3656 5b237745 Scott Ullrich
	return 0;
3657
}
3658
3659 42753d25 Ermal Lu?i
function interfaces_group_setup() {
3660
	global $config;
3661
3662
	if (!is_array($config['ifgroups']['ifgroupentry']))
3663
		return;
3664
3665 482961e3 Ermal Lu?i
	foreach ($config['ifgroups']['ifgroupentry'] as $groupar)
3666 42753d25 Ermal Lu?i
		interface_group_setup($groupar);
3667
3668
	return;
3669
}
3670
3671 abcb2bed Ermal Lu?i
function interface_group_setup(&$groupname /* The parameter is an array */) {
3672 42753d25 Ermal Lu?i
	global $config;
3673
3674
	if (!is_array($groupname))
3675
		return;
3676
	$members = explode(" ", $groupname['members']);
3677
	foreach($members as $ifs) {
3678
		$realif = get_real_interface($ifs);
3679
		if ($realif)
3680
			mwexec("/sbin/ifconfig {$realif} group {$groupname['ifname']}");
3681
	}
3682
3683
	return;
3684
}
3685 48f23632 Ermal
3686 06182467 Renato Botelho
function is_interface_group($if) {
3687
	global $config;
3688
3689
	if (is_array($config['ifgroups']['ifgroupentry']))
3690
		foreach ($config['ifgroups']['ifgroupentry'] as $groupentry) {
3691
			if ($groupentry['ifname'] === $if)
3692
				return true;
3693
		}
3694
3695
	return false;
3696
}
3697
3698 48f23632 Ermal
function interface_group_add_member($interface, $groupname) {
3699 ed62880b Ermal
	$interface = get_real_interface($interface);
3700 48f23632 Ermal
	mwexec("/sbin/ifconfig {$interface} group {$groupname}", true);
3701
}
3702 be45aa79 Renato Botelho
3703 e8910ad4 Ermal Lu?i
/* COMPAT Function */
3704 afb2de1b Ermal Lu?i
function convert_friendly_interface_to_real_interface_name($interface) {
3705
	return get_real_interface($interface);
3706
}
3707
3708 e8910ad4 Ermal Lu?i
/* COMPAT Function */
3709 eba938e3 Scott Ullrich
function get_real_wan_interface($interface = "wan") {
3710 abb31ea4 Ermal Luçi
	return get_real_interface($interface);
3711
}
3712 afb2de1b Ermal Lu?i
3713 e8910ad4 Ermal Lu?i
/* COMPAT Function */
3714 eba938e3 Scott Ullrich
function get_current_wan_address($interface = "wan") {
3715 abb31ea4 Ermal Luçi
	return get_interface_ip($interface);
3716
}
3717
3718 afb2de1b Ermal Lu?i
/*
3719
 * convert_real_interface_to_friendly_interface_name($interface): convert fxp0 -> wan, etc.
3720
 */
3721
function convert_real_interface_to_friendly_interface_name($interface = "wan") {
3722 7061ba0f Renato Botelho
	global $config;
3723 afb2de1b Ermal Lu?i
3724 7b47bd4c Ermal
	if (stristr($interface, "_vip")) {
3725 7061ba0f Renato Botelho
		foreach ($config['virtualip']['vip'] as $counter => $vip) {
3726
			if ($vip['mode'] == "carp")  {
3727
				if ($interface == "{$vip['interface']}_vip{$vip['vhid']}")
3728
					return $vip['interface'];
3729
			}
3730
		}
3731
	}
3732 afb2de1b Ermal Lu?i
3733 7061ba0f Renato Botelho
	/* XXX: For speed reasons reference directly the interface array */
3734 74e1e658 jim-p
	$ifdescrs = &$config['interfaces'];
3735 7061ba0f Renato Botelho
	//$ifdescrs = get_configured_interface_list(false, true);
3736 afb2de1b Ermal Lu?i
3737 1d66a364 Ermal
	if (strstr($interface, "_stf"))
3738
		$interface = str_replace("_stf", "", $interface);
3739
3740 7061ba0f Renato Botelho
	foreach ($ifdescrs as $if => $ifname) {
3741
		if ($if == $interface || $config['interfaces'][$if]['if'] == $interface)
3742
			return $if;
3743 afb2de1b Ermal Lu?i
3744 7061ba0f Renato Botelho
		if (stristr($interface, "_wlan0") && $config['interfaces'][$if]['if'] == interface_get_wireless_base($interface))
3745
			return $if;
3746 af637766 Erik Fonnesbeck
3747 d11e01f4 Erik Fonnesbeck
		// XXX: This case doesn't work anymore (segfaults - recursion?) - should be replaced with something else or just removed.
3748
		//      Not to be replaced with get_real_interface - causes slow interface listings here because of recursion!
3749
		/*
3750 7061ba0f Renato Botelho
		$int = get_parent_interface($if);
3751
		if ($int[0] == $interface)
3752
			return $ifname;
3753
		 */
3754
	}
3755 1d66a364 Ermal
3756 7061ba0f Renato Botelho
	return NULL;
3757 afb2de1b Ermal Lu?i
}
3758
3759
/* attempt to resolve interface to friendly descr */
3760
function convert_friendly_interface_to_friendly_descr($interface) {
3761 1c3ddd9e Renato Botelho
	global $config;
3762 afb2de1b Ermal Lu?i
3763 1c3ddd9e Renato Botelho
	switch ($interface) {
3764
	case "l2tp":
3765
		$ifdesc = "L2TP";
3766
		break;
3767 68ef6e03 Ermal
	case "pptp":
3768
		$ifdesc = "PPTP";
3769
		break;
3770
	case "pppoe":
3771
		$ifdesc = "PPPoE";
3772
		break;
3773
	case "openvpn":
3774
		$ifdesc = "OpenVPN";
3775
		break;
3776
	case "enc0":
3777
	case "ipsec":
3778
		$ifdesc = "IPsec";
3779
		break;
3780 1c3ddd9e Renato Botelho
	default:
3781
		if (isset($config['interfaces'][$interface])) {
3782
			if (empty($config['interfaces'][$interface]['descr']))
3783
				$ifdesc = strtoupper($interface);
3784
			else
3785
				$ifdesc = strtoupper($config['interfaces'][$interface]['descr']);
3786 57c52d45 Erik Fonnesbeck
			break;
3787 7b47bd4c Ermal
		} else if (stristr($interface, "_vip")) {
3788 68ef6e03 Ermal
			if (is_array($config['virtualip']['vip'])) {
3789
				foreach ($config['virtualip']['vip'] as $counter => $vip) {
3790 3e662cb0 Ermal
					if ($vip['mode'] == "carp")  {
3791 7b47bd4c Ermal
						if ($interface == "{$vip['interface']}_vip{$vip['vhid']}")
3792 68ef6e03 Ermal
							return "{$vip['subnet']} - {$vip['descr']}";
3793
					}
3794
				}
3795 1c3ddd9e Renato Botelho
			}
3796
		} else {
3797 68ef6e03 Ermal
			/* if list */
3798
			$ifdescrs = get_configured_interface_with_descr(false, true);
3799
			foreach ($ifdescrs as $if => $ifname) {
3800 7b47bd4c Ermal
				if ($if == $interface || $ifname == $interface)
3801
					return $ifname;
3802 68ef6e03 Ermal
			}
3803 57c52d45 Erik Fonnesbeck
		}
3804 1c3ddd9e Renato Botelho
		break;
3805
	}
3806 afb2de1b Ermal Lu?i
3807 1c3ddd9e Renato Botelho
	return $ifdesc;
3808 afb2de1b Ermal Lu?i
}
3809
3810
function convert_real_interface_to_friendly_descr($interface) {
3811 1c3ddd9e Renato Botelho
	global $config;
3812 afb2de1b Ermal Lu?i
3813 1c3ddd9e Renato Botelho
	$ifdesc = convert_real_interface_to_friendly_interface_name("{$interface}");
3814 afb2de1b Ermal Lu?i
3815 1c3ddd9e Renato Botelho
	if ($ifdesc) {
3816
		$iflist = get_configured_interface_with_descr(false, true);
3817
		return $iflist[$ifdesc];
3818
	}
3819 afb2de1b Ermal Lu?i
3820 1c3ddd9e Renato Botelho
	return $interface;
3821 afb2de1b Ermal Lu?i
}
3822
3823 532b0fb8 Ermal Lu?i
/*
3824 d5dfcb52 gnhb
 *  get_parent_interface($interface):
3825 20cb9803 gnhb
 *			--returns the (real or virtual) parent interface(s) array for a given interface friendly name (i.e. wan)
3826
 *				or virtual interface (i.e. vlan)
3827
 *				(We need array because MLPPP and bridge interfaces have more than one parent.)
3828
 *			-- returns $interface passed in if $interface parent is not found
3829
 *			-- returns empty array if an invalid interface is passed
3830
 *	(Only handles ppps and vlans now.)
3831 532b0fb8 Ermal Lu?i
 */
3832 d5dfcb52 gnhb
function get_parent_interface($interface) {
3833
	global $config;
3834 532b0fb8 Ermal Lu?i
3835 20cb9803 gnhb
	$parents = array();
3836
	//Check that we got a valid interface passed
3837
	$realif = get_real_interface($interface);
3838
	if ($realif == NULL)
3839
		return $parents;
3840
3841
	// If we got a real interface, find it's friendly assigned name
3842
	$interface = convert_real_interface_to_friendly_interface_name($interface);
3843 be45aa79 Renato Botelho
3844 20cb9803 gnhb
	if (!empty($interface) && isset($config['interfaces'][$interface])) {
3845
		$ifcfg = $config['interfaces'][$interface];
3846
		switch ($ifcfg['ipaddr']) {
3847
			case "ppp":
3848
			case "pppoe":
3849
			case "pptp":
3850
			case "l2tp":
3851
				if (empty($parents))
3852
					if (is_array($config['ppps']['ppp']))
3853
						foreach ($config['ppps']['ppp'] as $pppidx => $ppp) {
3854 02b8bfae Renato Botelho
							if ($ifcfg['if'] == $ppp['if']) {
3855 20cb9803 gnhb
								$ports = explode(',', $ppp['ports']);
3856 be45aa79 Renato Botelho
								foreach ($ports as $pid => $parent_if)
3857 20cb9803 gnhb
									$parents[$pid] = get_real_interface($parent_if);
3858
								break;
3859
							}
3860
						}
3861
				break;
3862
			case "dhcp":
3863
			case "static":
3864
			default:
3865
				// Handle _vlans
3866 76254caa Renato Botelho
				if (stristr($realif,"_vlan"))
3867 be45aa79 Renato Botelho
					if (is_array($config['vlans']['vlan']))
3868 20cb9803 gnhb
						foreach ($config['vlans']['vlan'] as $vlanidx => $vlan)
3869
							if ($ifcfg['if'] == $vlan['vlanif']){
3870
								$parents[0] = $vlan['if'];
3871
								break;
3872
							}
3873
				break;
3874 3e5d0d1d Ermal
		}
3875
	}
3876 be45aa79 Renato Botelho
3877 20cb9803 gnhb
	if (empty($parents))
3878
		$parents[0] = $realif;
3879 be45aa79 Renato Botelho
3880 20cb9803 gnhb
	return $parents;
3881 532b0fb8 Ermal Lu?i
}
3882
3883 263e2b7e Erik Fonnesbeck
function interface_is_wireless_clone($wlif) {
3884
	if(!stristr($wlif, "_wlan")) {
3885
		return false;
3886
	} else {
3887
		return true;
3888
	}
3889
}
3890
3891 1d072761 Erik Fonnesbeck
function interface_get_wireless_base($wlif) {
3892 34808d4e Erik Fonnesbeck
	if(!stristr($wlif, "_wlan")) {
3893
		return $wlif;
3894
	} else {
3895
		return substr($wlif, 0, stripos($wlif, "_wlan"));
3896
	}
3897
}
3898
3899 1d072761 Erik Fonnesbeck
function interface_get_wireless_clone($wlif) {
3900 34808d4e Erik Fonnesbeck
	if(!stristr($wlif, "_wlan")) {
3901
		return $wlif . "_wlan0";
3902
	} else {
3903
		return $wlif;
3904
	}
3905
}
3906
3907 b6c1f22f Ermal
function get_real_interface($interface = "wan", $family = "all") {
3908 ee3576dd Ermal
	global $config, $g;
3909 cfc707f7 Scott Ullrich
3910 521cfa2f Ermal Lu?i
	$wanif = NULL;
3911 c515ea57 Scott Ullrich
3912 67ee1ec5 Ermal Luçi
	switch ($interface) {
3913 acc1e9d0 Scott Ullrich
	case "l2tp":
3914
		$wanif = "l2tp";
3915
		break;
3916 67ee1ec5 Ermal Luçi
	case "pptp":
3917
		$wanif = "pptp";
3918
		break;
3919
	case "pppoe":
3920
		$wanif = "pppoe";
3921
		break;
3922
	case "openvpn":
3923
		$wanif = "openvpn";
3924
		break;
3925 4563d12f Seth Mos
	case "ipsec":
3926 67ee1ec5 Ermal Luçi
	case "enc0":
3927
		$wanif = "enc0";
3928
		break;
3929
	case "ppp":
3930
		$wanif = "ppp";
3931
		break;
3932
	default:
3933 6d5446a2 Ermal
		// If a real interface was alread passed simply
3934
		// pass the real interface back.  This encourages
3935
		// the usage of this function in more cases so that
3936
		// we can combine logic for more flexibility.
3937
		if(does_interface_exist($interface)) {
3938
			$wanif = $interface;
3939
			break;
3940
		}
3941 bf001dec smos
3942 6d5446a2 Ermal
		if (empty($config['interfaces'][$interface]))
3943
			break;
3944 568b1358 Scott Ullrich
3945 6447bde5 jim-p
		$cfg = &$config['interfaces'][$interface];
3946 2ebf3945 Scott Ullrich
3947 b6c1f22f Ermal
		if ($family == "inet6") {
3948
			switch ($cfg['ipaddrv6']) {
3949
			case "6rd":
3950
			case "6to4":
3951
				$wanif = "{$interface}_stf";
3952
				break;
3953
			default:
3954
				if( is_array($cfg['wireless']) || preg_match($g['wireless_regex'], $cfg['if']))
3955
					$wanif = interface_get_wireless_clone($cfg['if']);
3956
				else
3957
					$wanif = $cfg['if'];
3958
				break;
3959
			}
3960
		} else {
3961
			// Wireless cloned NIC support (FreeBSD 8+)
3962
			// interface name format: $parentnic_wlanparentnic#
3963
			// example: ath0_wlan0
3964
			if( is_array($cfg['wireless']) || preg_match($g['wireless_regex'], $cfg['if']))
3965
				$wanif = interface_get_wireless_clone($cfg['if']);
3966
			else
3967
				$wanif = $cfg['if'];
3968
		}
3969 67ee1ec5 Ermal Luçi
		break;
3970 c515ea57 Scott Ullrich
	}
3971
3972 1c3ddd9e Renato Botelho
	return $wanif;
3973 5b237745 Scott Ullrich
}
3974
3975 9ff8c299 Seth Mos
/* Guess the physical interface by providing a IP address */
3976 afb2de1b Ermal Lu?i
function guess_interface_from_ip($ipaddress) {
3977 80a2c1e6 Seth Mos
	if(! is_ipaddr($ipaddress)) {
3978 9ff8c299 Seth Mos
		return false;
3979
	}
3980 a05b2f42 Seth Mos
	if(is_ipaddrv4($ipaddress)) {
3981
		/* create a route table we can search */
3982
		exec("netstat -rnWf inet", $output, $ret);
3983
		foreach($output as $line) {
3984
			if(preg_match("/^[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+\/[0-9]+[ ]+link[#]/", $line)) {
3985
				$fields = preg_split("/[ ]+/", $line);
3986
				if(ip_in_subnet($ipaddress, $fields[0])) {
3987
					return $fields[6];
3988
				}
3989
			}
3990
		}
3991
	}
3992
	/* FIXME: This works from cursory testing, regexp might need fine tuning */
3993
	if(is_ipaddrv6($ipaddress)) {
3994
		/* create a route table we can search */
3995
		exec("netstat -rnWf inet6", $output, $ret);
3996
		foreach($output as $line) {
3997
			if(preg_match("/[0-9a-f]+[:]+[0-9a-f]+[:]+[\/][0-9]+/", $line)) {
3998
				$fields = preg_split("/[ ]+/", $line);
3999
				if(ip_in_subnet($ipaddress, $fields[0])) {
4000
					return $fields[6];
4001
				}
4002 9ff8c299 Seth Mos
			}
4003
		}
4004
	}
4005
	$ret = exec_command("/sbin/route -n get {$ipaddress} | /usr/bin/awk '/interface/ { print \$2; };'");
4006
	if(empty($ret)) {
4007 1c3ddd9e Renato Botelho
		return false;
4008 9ff8c299 Seth Mos
	}
4009
	return $ret;
4010 afb2de1b Ermal Lu?i
}
4011
4012
/*
4013
 * find_ip_interface($ip): return the interface where an ip is defined
4014 59231855 Darren Embry
 *   (or if $bits is specified, where an IP within the subnet is defined)
4015 afb2de1b Ermal Lu?i
 */
4016 2027b4c7 bcyrill
function find_ip_interface($ip, $bits = null) {
4017
	if (!is_ipaddr($ip))
4018
		return false;
4019
	
4020
	$isv6ip = is_ipaddrv6($ip);
4021
	
4022 59231855 Darren Embry
	/* if list */
4023
	$ifdescrs = get_configured_interface_list();
4024 be45aa79 Renato Botelho
4025 59231855 Darren Embry
	foreach ($ifdescrs as $ifdescr => $ifname) {
4026 2027b4c7 bcyrill
		$ifip = ($isv6ip) ? get_interface_ipv6($ifname) : get_interface_ip($ifname);
4027 ec8b4d8d Ermal
		if (is_null($ifip))
4028 2027b4c7 bcyrill
			continue;
4029 ec8b4d8d Ermal
		if (is_null($bits)) {
4030 2027b4c7 bcyrill
			if ($ip == $ifip) {
4031 59231855 Darren Embry
				$int = get_real_interface($ifname);
4032
				return $int;
4033
			}
4034
		}
4035
		else {
4036 2027b4c7 bcyrill
			if (ip_in_subnet($ifip, $ip . "/" . $bits)) {
4037 59231855 Darren Embry
				$int = get_real_interface($ifname);
4038
				return $int;
4039
			}
4040
		}
4041
	}
4042 ec8b4d8d Ermal
4043 59231855 Darren Embry
	return false;
4044
}
4045 afb2de1b Ermal Lu?i
4046 59231855 Darren Embry
/*
4047
 * find_virtual_ip_alias($ip): return the virtual IP alias where an IP is found
4048
 *   (or if $bits is specified, where an IP within the subnet is found)
4049
 */
4050
function find_virtual_ip_alias($ip, $bits = null) {
4051
	global $config;
4052 6b207f73 bcyrill
	
4053 59231855 Darren Embry
	if (!is_array($config['virtualip']['vip'])) {
4054
		return false;
4055
	}
4056 6b207f73 bcyrill
	if (!is_ipaddr($ip))
4057
		return false;
4058
	
4059
	$isv6ip = is_ipaddrv6($ip);
4060
	
4061 59231855 Darren Embry
	foreach ($config['virtualip']['vip'] as $vip) {
4062
		if ($vip['mode'] === "ipalias") {
4063 6b207f73 bcyrill
			if (is_ipaddrv6($vip['subnet']) != $isv6ip)
4064
				continue;
4065 ec8b4d8d Ermal
			if (is_null($bits)) {
4066 59231855 Darren Embry
				if (ip_in_subnet($ip, $vip['subnet'] . "/" . $vip['subnet_bits'])) {
4067
					return $vip;
4068
				}
4069
			}
4070
			else {
4071 dbea91b3 bcyrill
				if (($isv6ip && check_subnetsv6_overlap($ip, $bits, $vip['subnet'], $vip['subnet_bits']))
4072
					|| (!$isv6ip && check_subnets_overlap($ip, $bits, $vip['subnet'], $vip['subnet_bits']))) {
4073 59231855 Darren Embry
					return $vip;
4074
				}
4075
			}
4076 abcb2bed Ermal Lu?i
		}
4077 59231855 Darren Embry
	}
4078
	return false;
4079 afb2de1b Ermal Lu?i
}
4080
4081 a71b32d2 Scott Ullrich
/*
4082
 *   find_number_of_created_carp_interfaces: return the number of carp interfaces
4083
 */
4084
function find_number_of_created_carp_interfaces() {
4085
	return `/sbin/ifconfig | grep "carp:" | wc -l`;
4086
}
4087
4088
function get_all_carp_interfaces() {
4089
	$ints = str_replace("\n", " ", `ifconfig | grep "carp:" -B2 | grep ": flag" | cut -d: -f1`);
4090 81c64284 Chris Buechler
	$ints = explode(" ", $ints);
4091 a71b32d2 Scott Ullrich
	return $ints;
4092
}
4093
4094 abcb2bed Ermal Lu?i
/*
4095
 * find_carp_interface($ip): return the carp interface where an ip is defined
4096
 */
4097
function find_carp_interface($ip) {
4098 27625b39 Scott Ullrich
	global $config;
4099 abcb2bed Ermal Lu?i
	if (is_array($config['virtualip']['vip'])) {
4100
		foreach ($config['virtualip']['vip'] as $vip) {
4101 3e662cb0 Ermal
			if ($vip['mode'] == "carp") {
4102 645ad665 Seth Mos
				if(is_ipaddrv4($ip)) {
4103
					$carp_ip = get_interface_ip($vip['interface']);
4104
				}
4105
				if(is_ipaddrv6($ip)) {
4106
					$carp_ip = get_interface_ipv6($vip['interface']);
4107
				}
4108
				exec("/sbin/ifconfig", $output, $return);
4109
				foreach($output as $line) {
4110
					$elements = preg_split("/[ ]+/i", $line);
4111
					if(strstr($elements[0], "vip"))
4112
						$curif = str_replace(":", "", $elements[0]);
4113
					if(stristr($line, $ip)) {
4114
						$if = $curif;
4115
						continue;
4116
					}
4117
				}
4118 a687f866 Namezero
4119 27625b39 Scott Ullrich
				if ($if)
4120
					return $if;
4121 abcb2bed Ermal Lu?i
			}
4122
		}
4123
	}
4124
}
4125
4126
function link_carp_interface_to_parent($interface) {
4127 6fb26a17 smos
	global $config;
4128 abcb2bed Ermal Lu?i
4129 6fb26a17 smos
	if ($interface == "")
4130
		return;
4131 abcb2bed Ermal Lu?i
4132 6fb26a17 smos
	$carp_ip = get_interface_ip($interface);
4133
	$carp_ipv6 = get_interface_ipv6($interface);
4134 abcb2bed Ermal Lu?i
4135 6fb26a17 smos
	if((!is_ipaddrv4($carp_ip)) && (!is_ipaddrv6($carp_ipv6)))
4136
		return;
4137 abcb2bed Ermal Lu?i
4138 6fb26a17 smos
	/* if list */
4139
	$ifdescrs = get_configured_interface_list();
4140
	foreach ($ifdescrs as $ifdescr => $ifname) {
4141
		/* check IPv4 */
4142
		if(is_ipaddrv4($carp_ip)) {
4143
			$interfaceip = get_interface_ip($ifname);
4144
			$subnet_bits = get_interface_subnet($ifname);
4145
			$subnet_ip = gen_subnet("{$interfaceip}", "{$subnet_bits}");
4146
			if(ip_in_subnet($carp_ip, "{$subnet_ip}/{$subnet_bits}"))
4147
				return $ifname;
4148
		}
4149
		/* Check IPv6 */
4150
		if(is_ipaddrv6($carp_ipv6)) {
4151
			$interfaceipv6 = get_interface_ipv6($ifname);
4152
			$prefixlen = get_interface_subnetv6($ifname);
4153
			if(ip_in_subnet($carp_ipv6, "{$interfaceipv6}/{$prefixlen}"))
4154
				return $ifname;
4155
		}
4156
	}
4157
	return "";
4158 abcb2bed Ermal Lu?i
}
4159
4160 6fb26a17 smos
4161 abcb2bed Ermal Lu?i
/****f* interfaces/link_ip_to_carp_interface
4162
 * NAME
4163
 *   link_ip_to_carp_interface - Find where a CARP interface links to.
4164
 * INPUTS
4165
 *   $ip
4166
 * RESULT
4167
 *   $carp_ints
4168
 ******/
4169
function link_ip_to_carp_interface($ip) {
4170 1c3ddd9e Renato Botelho
	global $config;
4171 abcb2bed Ermal Lu?i
4172 1c3ddd9e Renato Botelho
	if (!is_ipaddr($ip))
4173
		return;
4174 abcb2bed Ermal Lu?i
4175 1c3ddd9e Renato Botelho
	$carp_ints = "";
4176
	if (is_array($config['virtualip']['vip'])) {
4177 1d002dc9 Ermal
		$first = 0;
4178 3fbc3487 Ermal
		$carp_int = array();
4179 1c3ddd9e Renato Botelho
		foreach ($config['virtualip']['vip'] as $vip) {
4180
			if ($vip['mode'] == "carp") {
4181
				$carp_ip = $vip['subnet'];
4182
				$carp_sn = $vip['subnet_bits'];
4183
				$carp_nw = gen_subnet($carp_ip, $carp_sn);
4184
				if (ip_in_subnet($ip, "{$carp_nw}/{$carp_sn}")) {
4185 7b47bd4c Ermal
					$carp_int[] = "{$vip['interface']}_vip{$vip['vhid']}";
4186
				}
4187 1c3ddd9e Renato Botelho
			}
4188
		}
4189 3fbc3487 Ermal
		if (!empty($carp_int))
4190
			$carp_ints = implode(" ", array_unique($carp_int));
4191 1c3ddd9e Renato Botelho
	}
4192 abcb2bed Ermal Lu?i
4193 1c3ddd9e Renato Botelho
	return $carp_ints;
4194 abcb2bed Ermal Lu?i
}
4195
4196 7a04cd20 Ermal
function link_interface_to_track6($int, $action = "") {
4197
	global $config;
4198
4199
	if (empty($int))
4200
		return;
4201
4202
	if (is_array($config['interfaces'])) {
4203
		$list = array();
4204
		foreach ($config['interfaces'] as $ifname => $ifcfg) {
4205
			if (!isset($ifcfg['enable']))
4206
				continue;
4207
			if (!empty($ifcfg['ipaddrv6']) && $ifcfg['track6-interface'] == $int) {
4208
				if ($action == "update")
4209
					interface_track6_configure($ifname, $ifcfg);
4210
				else if ($action == "")
4211
					$list[$ifname] = $ifcfg;
4212
			}
4213
		}
4214
		return $list;
4215
	}
4216
}
4217
4218 7850de1c Ermal Lu?i
function link_interface_to_vlans($int, $action = "") {
4219
	global $config;
4220
4221
	if (empty($int))
4222
		return;
4223
4224
	if (is_array($config['vlans']['vlan'])) {
4225 a362a23a Ermal
		$ifaces = array();
4226 1c3ddd9e Renato Botelho
		foreach ($config['vlans']['vlan'] as $vlan) {
4227 fa4a331f Ermal
			if ($int == $vlan['if']) {
4228 7850de1c Ermal Lu?i
				if ($action == "update") {
4229 fa4a331f Ermal
					interfaces_bring_up($int);
4230 7850de1c Ermal Lu?i
				} else if ($action == "")
4231 a362a23a Ermal
					$ifaces[$vlan['tag']] = $vlan;
4232 7850de1c Ermal Lu?i
			}
4233
		}
4234 a362a23a Ermal
		if (!empty($ifaces))
4235
			return $ifaces;
4236 7850de1c Ermal Lu?i
	}
4237
}
4238
4239
function link_interface_to_vips($int, $action = "") {
4240 1c3ddd9e Renato Botelho
	global $config;
4241 e5ac67ed Ermal Lu?i
4242 1c3ddd9e Renato Botelho
	if (is_array($config['virtualip']['vip'])) {
4243 75201355 Ermal
		$result = array();
4244 dcadda55 Ermal
		foreach ($config['virtualip']['vip'] as $vip) {
4245
			if ($int == $vip['interface']) {
4246 7b47bd4c Ermal
				if ($action == "update")
4247
					interfaces_vips_configure($int);
4248
				else
4249 75201355 Ermal
					$result[] = $vip;
4250 7850de1c Ermal Lu?i
			}
4251 dcadda55 Ermal
		}
4252 75201355 Ermal
		return $result;
4253 dcadda55 Ermal
	}
4254 e5ac67ed Ermal Lu?i
}
4255
4256 afb2de1b Ermal Lu?i
/****f* interfaces/link_interface_to_bridge
4257
 * NAME
4258
 *   link_interface_to_bridge - Finds out a bridge group for an interface
4259
 * INPUTS
4260
 *   $ip
4261
 * RESULT
4262
 *   bridge[0-99]
4263
 ******/
4264
function link_interface_to_bridge($int) {
4265 1c3ddd9e Renato Botelho
	global $config;
4266 afb2de1b Ermal Lu?i
4267 1c3ddd9e Renato Botelho
	if (is_array($config['bridges']['bridged'])) {
4268
		foreach ($config['bridges']['bridged'] as $bridge) {
4269 a639bb91 Ermal
			if (in_array($int, explode(',', $bridge['members'])))
4270 1c3ddd9e Renato Botelho
				return "{$bridge['bridgeif']}";
4271 a639bb91 Ermal
		}
4272
	}
4273 afb2de1b Ermal Lu?i
}
4274
4275 48f23632 Ermal
function link_interface_to_group($int) {
4276 1c3ddd9e Renato Botelho
	global $config;
4277 48f23632 Ermal
4278 ed62880b Ermal
	$result = array();
4279
4280 1c3ddd9e Renato Botelho
	if (is_array($config['ifgroups']['ifgroupentry'])) {
4281
		foreach ($config['ifgroups']['ifgroupentry'] as $group) {
4282 1dbc0c43 Ermal
			if (in_array($int, explode(" ", $group['members'])))
4283 ed62880b Ermal
				$result[$group['ifname']] = $int;
4284 48f23632 Ermal
		}
4285
	}
4286 ed62880b Ermal
4287
	return $result;
4288 48f23632 Ermal
}
4289
4290 afb2de1b Ermal Lu?i
function link_interface_to_gre($interface) {
4291 1c3ddd9e Renato Botelho
	global $config;
4292 afb2de1b Ermal Lu?i
4293 ed62880b Ermal
	$result = array();
4294
4295 1c3ddd9e Renato Botelho
	if (is_array($config['gres']['gre'])) {
4296
		foreach ($config['gres']['gre'] as $gre)
4297
			if($gre['if'] == $interface)
4298 ed62880b Ermal
				$result[] = $gre;
4299
	}
4300
4301
	return $result;
4302 afb2de1b Ermal Lu?i
}
4303
4304
function link_interface_to_gif($interface) {
4305 1c3ddd9e Renato Botelho
	global $config;
4306 afb2de1b Ermal Lu?i
4307 ed62880b Ermal
	$result = array();
4308
4309 1c3ddd9e Renato Botelho
	if (is_array($config['gifs']['gif'])) {
4310
		foreach ($config['gifs']['gif'] as $gif)
4311
			if($gif['if'] == $interface)
4312
				$result[] = $gif;
4313 ed62880b Ermal
	}
4314
4315
	return $result;
4316 afb2de1b Ermal Lu?i
}
4317
4318
/*
4319
 * find_interface_ip($interface): return the interface ip (first found)
4320
 */
4321
function find_interface_ip($interface, $flush = false)
4322
{
4323
	global $interface_ip_arr_cache;
4324 01f1b601 Ermal
	global $interface_sn_arr_cache;
4325 afb2de1b Ermal Lu?i
4326
	$interface = str_replace("\n", "", $interface);
4327 be45aa79 Renato Botelho
4328 8256f324 gnhb
	if (!does_interface_exist($interface))
4329 afb2de1b Ermal Lu?i
		return;
4330
4331
	/* Setup IP cache */
4332
	if (!isset($interface_ip_arr_cache[$interface]) or $flush) {
4333 3f70e618 Ermal Lu?i
		$ifinfo = pfSense_get_interface_addresses($interface);
4334
		$interface_ip_arr_cache[$interface] = $ifinfo['ipaddr'];
4335 01f1b601 Ermal
		$interface_sn_arr_cache[$interface] = $ifinfo['subnetbits'];
4336 afb2de1b Ermal Lu?i
	}
4337
4338
	return $interface_ip_arr_cache[$interface];
4339
}
4340
4341 47593ac6 Seth Mos
/*
4342
 * find_interface_ipv6($interface): return the interface ip (first found)
4343
 */
4344
function find_interface_ipv6($interface, $flush = false)
4345
{
4346
	global $interface_ipv6_arr_cache;
4347
	global $interface_snv6_arr_cache;
4348 31ace4ea Seth Mos
	global $config;
4349 be45aa79 Renato Botelho
4350 31bdb9e5 smos
	$interface = trim($interface);
4351
	$interface = get_real_interface($interface);
4352 be45aa79 Renato Botelho
4353 47593ac6 Seth Mos
	if (!does_interface_exist($interface))
4354
		return;
4355
4356
	/* Setup IP cache */
4357
	if (!isset($interface_ipv6_arr_cache[$interface]) or $flush) {
4358 3c5e10fc Seth Mos
		// FIXME: Add IPv6 support to the pfSense module
4359 1d66a364 Ermal
		$ifinfo = array();
4360 31ace4ea Seth Mos
		exec("/sbin/ifconfig {$interface} inet6", $output);
4361
		foreach($output as $line) {
4362
			if(preg_match("/inet6/", $line)) {
4363
				$parts = explode(" ", $line);
4364 c9d174df Seth Mos
				if(! preg_match("/fe80::/", $parts[1])) {
4365 31ace4ea Seth Mos
					$ifinfo['ipaddrv6'] = $parts[1];
4366 a23a99cb Seth Mos
					if($parts[2] == "-->") {
4367 cf6bc278 Seth Mos
						$parts[5] = "126";
4368 9991ff2c Seth Mos
						$ifinfo['subnetbitsv6'] = $parts[5];
4369 a23a99cb Seth Mos
					} else {
4370 9991ff2c Seth Mos
						$ifinfo['subnetbitsv6'] = $parts[3];
4371 a23a99cb Seth Mos
					}
4372 acc68ffa Renato Botelho
					break;
4373 31ace4ea Seth Mos
				}
4374
			}
4375
		}
4376 47593ac6 Seth Mos
		$interface_ipv6_arr_cache[$interface] = $ifinfo['ipaddrv6'];
4377
		$interface_snv6_arr_cache[$interface] = $ifinfo['subnetbitsv6'];
4378
	}
4379
4380
	return $interface_ipv6_arr_cache[$interface];
4381
}
4382
4383 81a3b6f5 smos
/*
4384
 * find_interface_ipv6_ll($interface): return the interface ipv6 link local (first found)
4385
 */
4386
function find_interface_ipv6_ll($interface, $flush = false)
4387
{
4388 58418355 smos
	global $interface_llv6_arr_cache;
4389 81a3b6f5 smos
	global $config;
4390 be45aa79 Renato Botelho
4391 81a3b6f5 smos
	$interface = str_replace("\n", "", $interface);
4392 be45aa79 Renato Botelho
4393 81a3b6f5 smos
	if (!does_interface_exist($interface))
4394
		return;
4395
4396
	/* Setup IP cache */
4397 58418355 smos
	if (!isset($interface_llv6_arr_cache[$interface]) or $flush) {
4398 81a3b6f5 smos
		$ifinfo = pfSense_get_interface_addresses($interface);
4399
		// FIXME: Add IPv6 support to the pfSense module
4400
		exec("/sbin/ifconfig {$interface} inet6", $output);
4401
		foreach($output as $line) {
4402
			if(preg_match("/inet6/", $line)) {
4403
				$parts = explode(" ", $line);
4404
				if(preg_match("/fe80::/", $parts[1])) {
4405 58418355 smos
					$partsaddress = explode("%", $parts[1]);
4406
					$ifinfo['linklocal'] = $partsaddress[0];
4407 81a3b6f5 smos
				}
4408
			}
4409
		}
4410 58418355 smos
		$interface_llv6_arr_cache[$interface] = $ifinfo['linklocal'];
4411 81a3b6f5 smos
	}
4412 58418355 smos
	return $interface_llv6_arr_cache[$interface];
4413 81a3b6f5 smos
}
4414
4415 afb2de1b Ermal Lu?i
function find_interface_subnet($interface, $flush = false)
4416
{
4417
	global $interface_sn_arr_cache;
4418 01f1b601 Ermal
	global $interface_ip_arr_cache;
4419 afb2de1b Ermal Lu?i
4420
	$interface = str_replace("\n", "", $interface);
4421
	if (does_interface_exist($interface) == false)
4422
		return;
4423
4424
	if (!isset($interface_sn_arr_cache[$interface]) or $flush) {
4425 bd96e1fe Ermal Lu?i
		$ifinfo = pfSense_get_interface_addresses($interface);
4426 01f1b601 Ermal
		$interface_ip_arr_cache[$interface] = $ifinfo['ipaddr'];
4427 bd96e1fe Ermal Lu?i
		$interface_sn_arr_cache[$interface] = $ifinfo['subnetbits'];
4428 1c3ddd9e Renato Botelho
	}
4429 afb2de1b Ermal Lu?i
4430
	return $interface_sn_arr_cache[$interface];
4431
}
4432
4433 47593ac6 Seth Mos
function find_interface_subnetv6($interface, $flush = false)
4434
{
4435
	global $interface_snv6_arr_cache;
4436
	global $interface_ipv6_arr_cache;
4437
4438
	$interface = str_replace("\n", "", $interface);
4439
	if (does_interface_exist($interface) == false)
4440
		return;
4441
4442 c4fc2eae Ermal
	$foundv6 = false;
4443 47593ac6 Seth Mos
	if (!isset($interface_snv6_arr_cache[$interface]) or $flush) {
4444 a56d8b08 Ermal
		$ifinfo = array();
4445 3c5e10fc Seth Mos
		// FIXME: Add IPv6 support to the pfSense module
4446 c4fc2eae Ermal
		unset($output);
4447 9991ff2c Seth Mos
		exec("/sbin/ifconfig {$interface} inet6", $output);
4448
		foreach($output as $line) {
4449 c4fc2eae Ermal
			$line = trim($line);
4450 9991ff2c Seth Mos
			if(preg_match("/inet6/", $line)) {
4451
				$parts = explode(" ", $line);
4452
				if(! preg_match("/fe80::/", $parts[1])) {
4453
					$ifinfo['ipaddrv6'] = $parts[1];
4454 a23a99cb Seth Mos
					if($parts[2] == "-->") {
4455 cf6bc278 Seth Mos
						$parts[5] = "126";
4456 9991ff2c Seth Mos
						$ifinfo['subnetbitsv6'] = $parts[5];
4457 a23a99cb Seth Mos
					} else {
4458 9991ff2c Seth Mos
						$ifinfo['subnetbitsv6'] = $parts[3];
4459 a23a99cb Seth Mos
					}
4460 c4fc2eae Ermal
					$foundv6 = true;
4461
					break;
4462 9991ff2c Seth Mos
				}
4463
			}
4464
		}
4465 c4fc2eae Ermal
		if ($foundv6 === true) {
4466
			$interface_ipv6_arr_cache[$interface] = $ifinfo['ipaddrv6'];
4467
			$interface_snv6_arr_cache[$interface] = $ifinfo['subnetbitsv6'];
4468
		} else
4469
			unset($interface_ipv6_arr_cache[$interface], $interface_snv6_arr_cache[$interface]);
4470 1c3ddd9e Renato Botelho
	}
4471 47593ac6 Seth Mos
4472
	return $interface_snv6_arr_cache[$interface];
4473
}
4474
4475 e19b7d1e Ermal
function ip_in_interface_alias_subnet($interface, $ipalias) {
4476
	global $config;
4477
4478
	if (empty($interface) || !is_ipaddr($ipalias))
4479 e8471084 Ermal
		return false;
4480 e19b7d1e Ermal
	if (is_array($config['virtualip']['vip'])) {
4481 1c3ddd9e Renato Botelho
		foreach ($config['virtualip']['vip'] as $vip) {
4482
			switch ($vip['mode']) {
4483
			case "ipalias":
4484
				if ($vip['interface'] <> $interface)
4485
					break;
4486 e19b7d1e Ermal
				if (ip_in_subnet($ipalias, gen_subnet($vip['subnet'], $vip['subnet_bits']) . "/" . $vip['subnet_bits']))
4487 e8471084 Ermal
					return true;
4488 1c3ddd9e Renato Botelho
				break;
4489
			}
4490
		}
4491 e19b7d1e Ermal
	}
4492 e8471084 Ermal
4493
	return false;
4494 e19b7d1e Ermal
}
4495
4496 e88fbe50 Ermal Lu?i
function get_interface_ip($interface = "wan")
4497
{
4498 bf001dec smos
	$realif = get_failover_interface($interface);
4499 afb2de1b Ermal Lu?i
	if (!$realif) {
4500
		if (preg_match("/^carp/i", $interface))
4501
			$realif = $interface;
4502 5a61fd69 smos
		else if (preg_match("/^[a-z0-9]+_vip/i", $interface))
4503 564df7c2 Ermal Lu?i
			$realif = $interface;
4504 afb2de1b Ermal Lu?i
		else
4505
			return null;
4506
	}
4507
4508 5e041d5f Scott Ullrich
	$curip = find_interface_ip($realif);
4509
	if ($curip && is_ipaddr($curip) && ($curip != "0.0.0.0"))
4510
		return $curip;
4511 8256f324 gnhb
	else
4512
		return null;
4513 5b237745 Scott Ullrich
}
4514
4515 b6c1f22f Ermal
function get_interface_ipv6($interface = "wan", $flush = false)
4516 47593ac6 Seth Mos
{
4517 479f0fda smos
	global $config;
4518 c4fc2eae Ermal
4519 909de400 Ermal
	$realif = get_failover_interface($interface, "inet6");
4520 47593ac6 Seth Mos
	if (!$realif) {
4521 c4fc2eae Ermal
		if (preg_match("/^[a-z0-9]+_vip/i", $interface))
4522 47593ac6 Seth Mos
			$realif = $interface;
4523
		else
4524
			return null;
4525
	}
4526
4527 b6c1f22f Ermal
	$curip = find_interface_ipv6($realif, $flush);
4528 47593ac6 Seth Mos
	if ($curip && is_ipaddrv6($curip) && ($curip != "::"))
4529
		return $curip;
4530
	else
4531
		return null;
4532
}
4533
4534 58418355 smos
function get_interface_linklocal($interface = "wan")
4535
{
4536 bf001dec smos
	$realif = get_failover_interface($interface);
4537 58418355 smos
	if (!$realif) {
4538
		if (preg_match("/^carp/i", $interface))
4539
			$realif = $interface;
4540 5a61fd69 smos
		else if (preg_match("/^[a-z0-9]+_vip/i", $interface))
4541 58418355 smos
			$realif = $interface;
4542
		else
4543
			return null;
4544
	}
4545
4546
	$curip = find_interface_ipv6_ll($realif);
4547
	if ($curip && is_ipaddrv6($curip) && ($curip != "::"))
4548
		return $curip;
4549
	else
4550
		return null;
4551
}
4552
4553 e88fbe50 Ermal Lu?i
function get_interface_subnet($interface = "wan")
4554
{
4555 31b24870 Ermal Luçi
	$realif = get_real_interface($interface);
4556 e88fbe50 Ermal Lu?i
	if (!$realif) {
4557 1c3ddd9e Renato Botelho
		if (preg_match("/^carp/i", $interface))
4558
			$realif = $interface;
4559
		else if (preg_match("/^[a-z0-9]+_vip/i", $interface))
4560
			$realif = $interface;
4561
		else
4562
			return null;
4563
	}
4564 e88fbe50 Ermal Lu?i
4565 5e041d5f Scott Ullrich
	$cursn = find_interface_subnet($realif);
4566
	if (!empty($cursn))
4567 31b24870 Ermal Luçi
		return $cursn;
4568
4569
	return null;
4570
}
4571
4572 47593ac6 Seth Mos
function get_interface_subnetv6($interface = "wan")
4573
{
4574 c4fc2eae Ermal
	global $config;
4575
4576 6fb66736 Ermal
	$realif = get_real_interface($interface, "inet6");
4577 47593ac6 Seth Mos
	if (!$realif) {
4578 c4fc2eae Ermal
		if (preg_match("/^[a-z0-9]+_vip/i", $interface))
4579 1c3ddd9e Renato Botelho
			$realif = $interface;
4580
		else
4581
			return null;
4582
	}
4583 47593ac6 Seth Mos
4584
	$cursn = find_interface_subnetv6($realif);
4585
	if (!empty($cursn))
4586
		return $cursn;
4587
4588
	return null;
4589
}
4590
4591 52947718 Ermal Lu?i
/* return outside interfaces with a gateway */
4592
function get_interfaces_with_gateway() {
4593 77ccab82 Scott Ullrich
	global $config;
4594 52947718 Ermal Lu?i
4595
	$ints = array();
4596
4597
	/* loop interfaces, check config for outbound */
4598 77ccab82 Scott Ullrich
	foreach($config['interfaces'] as $ifdescr => $ifname) {
4599
		switch ($ifname['ipaddr']) {
4600
			case "dhcp":
4601 39f750b5 gnhb
			case "ppp";
4602 77ccab82 Scott Ullrich
			case "pppoe":
4603
			case "pptp":
4604 6d5446a2 Ermal
			case "l2tp":
4605 9ebe7028 gnhb
			case "ppp";
4606 6d5446a2 Ermal
				$ints[$ifdescr] = $ifdescr;
4607 77ccab82 Scott Ullrich
			break;
4608
			default:
4609 c822154c jim-p
				if (substr($ifname['if'], 0, 4) ==  "ovpn" ||
4610 f6b30142 Ermal
				    !empty($ifname['gateway']))
4611 6d5446a2 Ermal
					$ints[$ifdescr] = $ifdescr;
4612 77ccab82 Scott Ullrich
			break;
4613
		}
4614
	}
4615
	return $ints;
4616 52947718 Ermal Lu?i
}
4617
4618
/* return true if interface has a gateway */
4619
function interface_has_gateway($friendly) {
4620 6d5446a2 Ermal
	global $config;
4621 52947718 Ermal Lu?i
4622 6d5446a2 Ermal
	if (!empty($config['interfaces'][$friendly])) {
4623 43a22ee2 jim-p
		$ifname = &$config['interfaces'][$friendly];
4624 6d5446a2 Ermal
		switch ($ifname['ipaddr']) {
4625
			case "dhcp":
4626
			case "pppoe":
4627
			case "pptp":
4628
			case "l2tp":
4629
			case "ppp";
4630
				return true;
4631
			break;
4632
			default:
4633 c822154c jim-p
				if (substr($ifname['if'], 0, 4) ==  "ovpn")
4634 e9d7afeb Ermal
					return true;
4635 6d5446a2 Ermal
				if (!empty($ifname['gateway']))
4636
					return true;
4637
			break;
4638
		}
4639
	}
4640 52947718 Ermal Lu?i
4641
	return false;
4642
}
4643
4644 2feb85af Seth Mos
/* return true if interface has a gateway */
4645
function interface_has_gatewayv6($friendly) {
4646
	global $config;
4647
4648
	if (!empty($config['interfaces'][$friendly])) {
4649
		$ifname = &$config['interfaces'][$friendly];
4650
		switch ($ifname['ipaddrv6']) {
4651 67102344 smos
			case "slaac":
4652 2feb85af Seth Mos
			case "dhcp6":
4653 a11a839d smos
			case "6to4":
4654 d500e296 smos
			case "6rd":
4655
				return true;
4656 a11a839d smos
				break;
4657 2feb85af Seth Mos
			default:
4658 c822154c jim-p
				if (substr($ifname['if'], 0, 4) ==  "ovpn")
4659 2feb85af Seth Mos
					return true;
4660
				if (!empty($ifname['gatewayv6']))
4661
					return true;
4662 a11a839d smos
				break;
4663 2feb85af Seth Mos
		}
4664
	}
4665
4666
	return false;
4667
}
4668
4669 a57b119e Bill Marquette
/****f* interfaces/is_altq_capable
4670
 * NAME
4671
 *   is_altq_capable - Test if interface is capable of using ALTQ
4672
 * INPUTS
4673
 *   $int            - string containing interface name
4674
 * RESULT
4675
 *   boolean         - true or false
4676
 ******/
4677
4678 eba938e3 Scott Ullrich
function is_altq_capable($int) {
4679 1c3ddd9e Renato Botelho
	/* Per:
4680
	 * http://www.freebsd.org/cgi/man.cgi?query=altq&manpath=FreeBSD+7.2-current&format=html
4681
	 * Only the following drivers have ALTQ support
4682
	 */
4683 c2d7074e Ermal
	$capable = array("age", "alc", "ale", "an", "ath", "aue", "awi", "bce",
4684 a5ccf623 jim-p
			"bfe", "bge", "bridge", "cas", "dc", "de", "ed", "em", "ep", "fxp", "gem",
4685 be888d7f Ermal
			"hme", "igb", "ipw", "iwi", "jme", "le", "lem", "msk", "mxge", "my", "nfe",
4686 8c62fa48 jim-p
			"npe", "nve", "ral", "re", "rl", "rum", "run", "bwn", "sf", "sis", "sk",
4687 64fe3233 Seth Mos
			"ste", "stge", "txp", "udav", "ural", "vge", "vr", "wi", "xl",
4688 febca7e8 Ermal
			"ndis", "tun", "ovpns", "ovpnc", "vlan", "pppoe", "pptp", "ng",
4689 cf205dca Ermal
			"l2tp", "ppp", "vtnet");
4690 a57b119e Bill Marquette
4691 2ccac125 Renato Botelho
	$int_family = remove_ifindex($int);
4692 a57b119e Bill Marquette
4693 2163ace9 phildd
	if (in_array($int_family, $capable))
4694 1c3ddd9e Renato Botelho
		return true;
4695 dbe67167 Ermal
	else if (stristr($int, "l2tp")) /* VLANs are name $parent_$vlan now */
4696
		return true;
4697 76254caa Renato Botelho
	else if (stristr($int, "_vlan")) /* VLANs are name $parent_$vlan now */
4698 7e627719 Ermal
		return true;
4699 21699e76 Ermal
	else if (stristr($int, "_wlan")) /* WLANs are name $parent_$wlan now */
4700 2f3446db Ermal Lu?i
		return true;
4701 1c3ddd9e Renato Botelho
	else
4702
		return false;
4703 a57b119e Bill Marquette
}
4704
4705 52947718 Ermal Lu?i
/****f* interfaces/is_interface_wireless
4706
 * NAME
4707
 *   is_interface_wireless - Returns if an interface is wireless
4708
 * RESULT
4709
 *   $tmp       - Returns if an interface is wireless
4710
 ******/
4711
function is_interface_wireless($interface) {
4712 1c3ddd9e Renato Botelho
	global $config, $g;
4713
4714
	$friendly = convert_real_interface_to_friendly_interface_name($interface);
4715
	if(!isset($config['interfaces'][$friendly]['wireless'])) {
4716
		if (preg_match($g['wireless_regex'], $interface)) {
4717
			if (isset($config['interfaces'][$friendly]))
4718
				$config['interfaces'][$friendly]['wireless'] = array();
4719
			return true;
4720
		}
4721
		return false;
4722
	} else
4723
		return true;
4724 52947718 Ermal Lu?i
}
4725
4726 eba938e3 Scott Ullrich
function get_wireless_modes($interface) {
4727 d8c67d69 Scott Ullrich
	/* return wireless modes and channels */
4728 92f7d37d Ermal Luçi
	$wireless_modes = array();
4729
4730 5357f386 Erik Fonnesbeck
	$cloned_interface = get_real_interface($interface);
4731 1b773d20 Ermal Lu?i
4732 5357f386 Erik Fonnesbeck
	if($cloned_interface && is_interface_wireless($cloned_interface)) {
4733 1b773d20 Ermal Lu?i
		$chan_list = "/sbin/ifconfig {$cloned_interface} list chan";
4734
		$stack_list = "/usr/bin/awk -F\"Channel \" '{ gsub(/\\*/, \" \"); print \$2 \"\\\n\" \$3 }'";
4735 1de74081 Ermal Lu?i
		$format_list = "/usr/bin/awk '{print \$5 \" \" \$6 \",\" \$1}'";
4736 d8c67d69 Scott Ullrich
4737 4b0e71db Scott Ullrich
		$interface_channels = "";
4738 d8c67d69 Scott Ullrich
		exec("$chan_list | $stack_list | sort -u | $format_list 2>&1", $interface_channels);
4739
		$interface_channel_count = count($interface_channels);
4740
4741
		$c = 0;
4742
		while ($c < $interface_channel_count)
4743
		{
4744
			$channel_line = explode(",", $interface_channels["$c"]);
4745
			$wireless_mode = trim($channel_line[0]);
4746
			$wireless_channel = trim($channel_line[1]);
4747 4066776d Scott Ullrich
			if(trim($wireless_mode) != "") {
4748
				/* if we only have 11g also set 11b channels */
4749
				if($wireless_mode == "11g") {
4750 1ae54336 Erik Fonnesbeck
					if(!isset($wireless_modes["11b"]))
4751
						$wireless_modes["11b"] = array();
4752 39c1349c Erik Fonnesbeck
				} else if($wireless_mode == "11g ht") {
4753 1ae54336 Erik Fonnesbeck
					if(!isset($wireless_modes["11b"]))
4754
						$wireless_modes["11b"] = array();
4755
					if(!isset($wireless_modes["11g"]))
4756
						$wireless_modes["11g"] = array();
4757 39c1349c Erik Fonnesbeck
					$wireless_mode = "11ng";
4758
				} else if($wireless_mode == "11a ht") {
4759 1ae54336 Erik Fonnesbeck
					if(!isset($wireless_modes["11a"]))
4760
						$wireless_modes["11a"] = array();
4761 39c1349c Erik Fonnesbeck
					$wireless_mode = "11na";
4762 4066776d Scott Ullrich
				}
4763
				$wireless_modes["$wireless_mode"]["$c"] = $wireless_channel;
4764
			}
4765 d8c67d69 Scott Ullrich
			$c++;
4766
		}
4767
	}
4768 4066776d Scott Ullrich
	return($wireless_modes);
4769 d8c67d69 Scott Ullrich
}
4770
4771 f4094f0d Erik Fonnesbeck
/* return channel numbers, frequency, max txpower, and max regulation txpower */
4772
function get_wireless_channel_info($interface) {
4773
	$wireless_channels = array();
4774
4775 5357f386 Erik Fonnesbeck
	$cloned_interface = get_real_interface($interface);
4776 f4094f0d Erik Fonnesbeck
4777 5357f386 Erik Fonnesbeck
	if($cloned_interface && is_interface_wireless($cloned_interface)) {
4778 f4094f0d Erik Fonnesbeck
		$chan_list = "/sbin/ifconfig {$cloned_interface} list txpower";
4779
		$stack_list = "/usr/bin/awk -F\"Channel \" '{ gsub(/\\*/, \" \"); print \$2 \"\\\n\" \$3 }'";
4780
		$format_list = "/usr/bin/awk '{print \$1 \",\" \$3 \" \" \$4 \",\" \$5 \",\" \$7}'";
4781
4782
		$interface_channels = "";
4783
		exec("$chan_list | $stack_list | sort -u | $format_list 2>&1", $interface_channels);
4784
4785
		foreach ($interface_channels as $channel_line) {
4786
			$channel_line = explode(",", $channel_line);
4787
			if(!isset($wireless_channels[$channel_line[0]]))
4788
				$wireless_channels[$channel_line[0]] = $channel_line;
4789
		}
4790
	}
4791
	return($wireless_channels);
4792
}
4793
4794 52947718 Ermal Lu?i
/****f* interfaces/get_interface_mtu
4795
 * NAME
4796
 *   get_interface_mtu - Return the mtu of an interface
4797
 * RESULT
4798
 *   $tmp       - Returns the mtu of an interface
4799
 ******/
4800
function get_interface_mtu($interface) {
4801 1c3ddd9e Renato Botelho
	$mtu = pfSense_get_interface_addresses($interface);
4802
	return $mtu['mtu'];
4803 52947718 Ermal Lu?i
}
4804
4805 eba938e3 Scott Ullrich
function get_interface_mac($interface) {
4806 7d6076f3 Ermal Lu?i
4807 3f70e618 Ermal Lu?i
	$macinfo = pfSense_get_interface_addresses($interface);
4808
	return $macinfo["macaddr"];
4809 f2ba47f8 Ermal Lu?i
}
4810
4811
/****f* pfsense-utils/generate_random_mac_address
4812
 * NAME
4813
 *   generate_random_mac - generates a random mac address
4814
 * INPUTS
4815
 *   none
4816
 * RESULT
4817
 *   $mac - a random mac address
4818
 ******/
4819
function generate_random_mac_address() {
4820 1c3ddd9e Renato Botelho
	$mac = "02";
4821
	for($x=0; $x<5; $x++)
4822
		$mac .= ":" . dechex(rand(16, 255));
4823
	return $mac;
4824 53c82ef9 Scott Ullrich
}
4825 b7ec2b9e Scott Ullrich
4826 52947718 Ermal Lu?i
/****f* interfaces/is_jumbo_capable
4827
 * NAME
4828
 *   is_jumbo_capable - Test if interface is jumbo frame capable.  Useful for determining VLAN capability.
4829
 * INPUTS
4830
 *   $int             - string containing interface name
4831
 * RESULT
4832
 *   boolean          - true or false
4833
 ******/
4834 47ee6926 Ermal
function is_jumbo_capable($iface) {
4835
	$iface = trim($iface);
4836
	$capable = pfSense_get_interface_addresses($iface);
4837 a687f866 Namezero
4838 1c3ddd9e Renato Botelho
	if (isset($capable['caps']['vlanmtu']))
4839
		return true;
4840 a687f866 Namezero
4841 47ee6926 Ermal
	return false;
4842 52947718 Ermal Lu?i
}
4843
4844 70e46e62 Ermal
function interface_setup_pppoe_reset_file($pppif, $iface="") {
4845 55f3ca1d gnhb
	global $g;
4846 70e46e62 Ermal
4847 5c8e8a17 gnhb
	$cron_file = "{$g['varetc_path']}/pppoe_restart_{$pppif}";
4848 766bd6d0 gnhb
4849 5c8e8a17 gnhb
	if(!empty($iface) && !empty($pppif)){
4850 7673cdb5 Ermal
		$cron_cmd = <<<EOD
4851
#!/bin/sh
4852
/usr/local/sbin/pfSctl -c 'interface reload {$iface}'
4853 70e46e62 Ermal
/usr/bin/logger -t {$pppif} "PPPoE periodic reset executed on {$iface}"
4854 7673cdb5 Ermal
4855
EOD;
4856
4857 70e46e62 Ermal
		@file_put_contents($cron_file, $cron_cmd);
4858
		chmod($cron_file, 0755);
4859 55f3ca1d gnhb
		sigkillbypid("{$g['varrun_path']}/cron.pid", "HUP");
4860 a5d6f60b Ermal Lu?i
	} else
4861 766bd6d0 gnhb
		unlink_if_exists($cron_file);
4862 b7ec2b9e Scott Ullrich
}
4863
4864 56da23dc Ermal
function get_interface_default_mtu($type = "ethernet") {
4865
	switch ($type) {
4866
	case "gre":
4867
		return 1476;
4868
		break;
4869
	case "gif":
4870
		return 1280;
4871
		break;
4872
	case "tun":
4873
	case "vlan":
4874
	case "tap":
4875
	case "ethernet":
4876
	default:
4877
		return 1500;
4878
		break;
4879
	}
4880
4881
	/* Never reached */
4882
	return 1500;
4883
}
4884
4885 dd62256f Pierre POMES
function get_vip_descr($ipaddress) {
4886
	global $config;
4887
4888
	foreach ($config['virtualip']['vip'] as $vip) {
4889
		if ($vip['subnet'] == $ipaddress) {
4890
			return ($vip['descr']);
4891
		}
4892
	}
4893
	return "";
4894
}
4895
4896 d368b334 jim-p
function interfaces_staticarp_configure($if) {
4897
	global $config, $g;
4898
	if(isset($config['system']['developerspew'])) {
4899
		$mt = microtime();
4900
		echo "interfaces_staticarp_configure($if) being called $mt\n";
4901
	}
4902
4903
	$ifcfg = $config['interfaces'][$if];
4904
4905 873e49ec Renato Botelho
	if (empty($if) || empty($ifcfg['if']) || !isset($ifcfg['enable']))
4906 d368b334 jim-p
		return 0;
4907
4908
	/* Enable staticarp, if enabled */
4909
	if(isset($config['dhcpd'][$if]['staticarp'])) {
4910
		mwexec("/sbin/ifconfig " . escapeshellarg($ifcfg['if']) . " staticarp " );
4911
		mwexec("/usr/sbin/arp -d -i " . escapeshellarg($ifcfg['if']) . " -a > /dev/null 2>&1 ");
4912
		if (is_array($config['dhcpd'][$if]['staticmap'])) {
4913
4914
			foreach ($config['dhcpd'][$if]['staticmap'] as $arpent) {
4915
				mwexec("/usr/sbin/arp -s " . escapeshellarg($arpent['ipaddr']) . " " . escapeshellarg($arpent['mac']));
4916
4917
			}
4918
4919
		}
4920
	} else {
4921
		mwexec("/sbin/ifconfig " . escapeshellarg($ifcfg['if']) . " -staticarp " );
4922
		mwexec("/usr/sbin/arp -d -i " . escapeshellarg($ifcfg['if']) . " -a > /dev/null 2>&1 ");
4923 25c1ebd5 N0YB
		if (is_array($config['dhcpd'][$if]['staticmap'])) {
4924
			foreach ($config['dhcpd'][$if]['staticmap'] as $arpent) {
4925
				if (isset($arpent['arp_table_static_entry'])) {
4926
					mwexec("/usr/sbin/arp -s " . escapeshellarg($arpent['ipaddr']) . " " . escapeshellarg($arpent['mac']));
4927
				}
4928
			}
4929
		}
4930 d368b334 jim-p
	}
4931
4932
	return 0;
4933
}
4934
4935 909de400 Ermal
function get_failover_interface($interface, $family = "all") {
4936 bf001dec smos
	global $config;
4937 e90c833a smos
	/* shortcut to get_real_interface if we find it in the config */
4938
	if(is_array($config['interfaces'][$interface])) {
4939 909de400 Ermal
		$wanif = get_real_interface($interface, $family);
4940 e90c833a smos
		return $wanif;
4941
	}
4942
4943 bf001dec smos
	/* compare against gateway groups */
4944
	$a_groups = return_gateway_groups_array();
4945
	if(is_array($a_groups[$interface])) {
4946
		/* we found a gateway group, fetch the interface or vip */
4947
		if($a_groups[$interface][0]['vip'] <> "")
4948
			$wanif = $a_groups[$interface][0]['vip'];
4949
		else
4950
			$wanif = $a_groups[$interface][0]['int'];
4951 be45aa79 Renato Botelho
4952 bf001dec smos
		return $wanif;
4953
	}
4954
	/* fall through to get_real_interface */
4955 909de400 Ermal
	$wanif = get_real_interface($interface, $family);
4956 bf001dec smos
	return $wanif;
4957
}
4958
4959 2ccac125 Renato Botelho
function remove_ifindex($ifname) {
4960
	return preg_replace("/[0-9]+$/", "", $ifname);
4961
}
4962
4963 6a7dd9bb Ermal
?>