Project

General

Profile

Download (10.6 KB) Statistics
| Branch: | Tag: | Revision:
1
<?php
2
/*
3
 * firewall_shaper.php
4
 *
5
 * part of pfSense (https://www.pfsense.org)
6
 * Copyright (c) 2004-2013 BSD Perimeter
7
 * Copyright (c) 2013-2016 Electric Sheep Fencing
8
 * Copyright (c) 2014-2024 Rubicon Communications, LLC (Netgate)
9
 * All rights reserved.
10
 *
11
 * Licensed under the Apache License, Version 2.0 (the "License");
12
 * you may not use this file except in compliance with the License.
13
 * You may obtain a copy of the License at
14
 *
15
 * http://www.apache.org/licenses/LICENSE-2.0
16
 *
17
 * Unless required by applicable law or agreed to in writing, software
18
 * distributed under the License is distributed on an "AS IS" BASIS,
19
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
20
 * See the License for the specific language governing permissions and
21
 * limitations under the License.
22
 */
23

    
24
##|+PRIV
25
##|*IDENT=page-firewall-trafficshaper
26
##|*NAME=Firewall: Traffic Shaper
27
##|*DESCR=Allow access to the 'Firewall: Traffic Shaper' page.
28
##|*MATCH=firewall_shaper.php*
29
##|-PRIV
30

    
31
require_once("guiconfig.inc");
32
require_once("functions.inc");
33
require_once("filter.inc");
34
require_once("shaper.inc");
35
require_once("rrd.inc");
36

    
37
$pgtitle = array(gettext("Firewall"), gettext("Traffic Shaper"), gettext("By Interface"));
38
$pglinks = array("", "@self", "@self");
39
$shortcut_section = "trafficshaper";
40

    
41
$shaperIFlist = get_configured_interface_with_descr(true);
42
read_altq_config();
43
/*
44
 * The whole logic in these code maybe can be specified.
45
 * If you find a better way contact me :).
46
 */
47

    
48
if ($_GET) {
49
	if ($_GET['queue']) {
50
		$qname = htmlspecialchars(trim($_GET['queue']));
51
	}
52
	if ($_GET['interface']) {
53
		$interface = htmlspecialchars(trim($_GET['interface']));
54
	}
55
	if ($_GET['action']) {
56
		$action = htmlspecialchars($_GET['action']);
57
	}
58
}
59

    
60
if ($_POST) {
61
	if ($_POST['name']) {
62
		$qname = htmlspecialchars(trim($_POST['name']));
63
	}
64
	if ($_POST['interface']) {
65
		$interface = htmlspecialchars(trim($_POST['interface']));
66
	}
67
	if ($_POST['parentqueue']) {
68
		$parentqueue = htmlspecialchars(trim($_POST['parentqueue']));
69
	}
70
}
71

    
72
if ($interface) {
73
	$altq = $altq_list_queues[$interface];
74

    
75
	if ($altq) {
76
		$queue =& $altq->find_queue($interface, $qname);
77
	} else {
78
		$addnewaltq = true;
79
	}
80
}
81

    
82
$dontshow = false;
83
$newqueue = false;
84
$dfltmsg = false;
85

    
86
if ($_GET) {
87
	switch ($action) {
88
	case "delete":
89
		if ($queue) {
90
			$queue->delete_queue();
91
			if (write_config("Traffic Shaper: Item deleted")) {
92
				mark_subsystem_dirty('shaper');
93
			}
94
		}
95

    
96
		header("Location: firewall_shaper.php");
97
		exit;
98
	case "resetall":
99
		foreach ($altq_list_queues as $altq) {
100
			$altq->delete_all();
101
		}
102
		unset($altq_list_queues);
103
		$altq_list_queues = array();
104
		$tree = "<ul class=\"tree\" >";
105
		$tree .= get_interface_list_to_show();
106
		$tree .= "</ul>";
107
		config_del_path('shaper/queue');
108
		unset($queue);
109
		unset($altq);
110
		$can_add = false;
111
		$can_enable = false;
112
		$dontshow = true;
113
		foreach (config_get_path('filter/rule', []) as $key => $rule) {
114
			if (isset($rule['wizard']) && $rule['wizard'] == "yes") {
115
				config_del_path("filter/rule/{$key}");
116
			}
117
		}
118

    
119
		if (write_config("Traffic Shaper: Reset all")) {
120
			$changes_applied = true;
121
			$retval = 0;
122
			$retval |= filter_configure();
123
		} else {
124
			$no_write_config_msg = gettext("Unable to write config.xml (Access Denied?).");
125
		}
126

    
127
		$dfltmsg = true;
128

    
129

    
130
		break;
131

    
132
	case "add":
133
		/* XXX: Find better way because we shouldn't know about this */
134
		if ($altq) {
135

    
136
			switch ($altq->GetScheduler()) {
137
			case "PRIQ":
138
				$q = new priq_queue();
139
				break;
140
			case "FAIRQ":
141
				$q = new fairq_queue();
142
				break;
143
			case "HFSC":
144
				$q = new hfsc_queue();
145
				break;
146
			case "CBQ":
147
				$q = new cbq_queue();
148
				break;
149
			default:
150
				/* XXX: Happens when sched==NONE?! */
151
				$q = new altq_root_queue();
152
				break;
153
			}
154
		} else if ($addnewaltq) {
155
			$q = new altq_root_queue();
156
		} else {
157
			$input_errors[] = gettext("Could not create new queue/discipline! Any recent changes may need to be applied first.");
158
		}
159

    
160
		if ($q) {
161
			$q->SetInterface($interface);
162
			$sform = $q->build_form();
163
			$sform->addGlobal(new Form_Input(
164
			    'parentqueue',
165
			    null,
166
			    'hidden',
167
			    $qname
168
			    ));
169

    
170
			$newjavascript = $q->build_javascript();
171
			unset($q);
172
			$newqueue = true;
173
		}
174
		break;
175
	case "show":
176
		if ($queue) {
177
			$sform = $queue->build_form();
178
		} else {
179
			$input_errors[] = gettext("Queue not found!");
180
		}
181
		break;
182
	case "enable":
183
		if ($queue) {
184
			$queue->SetEnabled("on");
185
			$sform = $queue->build_form();
186
			if (write_config("Traffic Shaper: Queue enabled")) {
187
				mark_subsystem_dirty('shaper');
188
			}
189
		} else {
190
			$input_errors[] = gettext("Queue not found!");
191
		}
192
		break;
193
	case "disable":
194
		if ($queue) {
195
			$queue->SetEnabled("");
196
			$sform = $queue->build_form();
197
			if (write_config("Traffic Shaper: Queue disabled")) {
198
				mark_subsystem_dirty('shaper');
199
			}
200
		} else {
201
			$input_errors[] = gettext("Queue not found!");
202
		}
203
		break;
204
	default:
205
		$dfltmsg = true;
206
		$dontshow = true;
207
		break;
208
	}
209
}
210

    
211
if ($_POST) {
212
	unset($input_errors);
213

    
214
	if ($addnewaltq) {
215
		$__tmp_altq = new altq_root_queue(); $altq =& $__tmp_altq;
216
		$altq->SetInterface($interface);
217
		$altq->ReadConfig($_POST);
218
		$altq->validate_input($_POST, $input_errors);
219
		if (!$input_errors) {
220
			unset($tmppath);
221
			$tmppath[] = $altq->GetInterface();
222
			$altq->SetLink($tmppath);
223
			$altq->wconfig();
224
			if (write_config("Traffic Shaper: Added root queue")) {
225
				mark_subsystem_dirty('shaper');
226
			}
227
			$can_enable = true;
228
			$can_add = true;
229
		}
230

    
231
		read_altq_config();
232
		$sform = $altq->build_form();
233
	} else if ($parentqueue) { /* Add a new queue */
234
		$qtmp =& $altq->find_queue($interface, $parentqueue);
235
		if ($qtmp) {
236
			$tmppath =& $qtmp->GetLink();
237
			array_push($tmppath, $qname);
238
			$tmp =& $qtmp->add_queue($interface, $_POST, $tmppath, $input_errors);
239
			if (!$input_errors) {
240
				array_pop($tmppath);
241
				$tmp->wconfig();
242
				$can_enable = true;
243
				if ($tmp->CanHaveChildren() && $can_enable) {
244
					if ($tmp->GetDefault() <> "") {
245
						$can_add = false;
246
					} else {
247
						$can_add = true;
248
					}
249
				} else {
250
					$can_add = false;
251
				}
252
				if (write_config("Traffic Shaper: Added new queue")) {
253
					mark_subsystem_dirty('shaper');
254
				}
255
				$can_enable = true;
256
				if ($altq->GetScheduler() != "PRIQ") { /* XXX */
257
					if ($tmp->GetDefault() <> "") {
258
						$can_add = false;
259
					} else {
260
						$can_add = true;
261
					}
262
				}
263
			}
264
			read_altq_config();
265
			$sform = $tmp->build_form();
266
		} else {
267
			$input_errors[] = gettext("Could not add new queue.");
268
		}
269
	} else if ($_POST['apply']) {
270
		write_config("Traffic Shaper: Apply changes");
271
		$changes_applied = true;
272
		$retval = 0;
273
		$retval |= filter_configure();
274

    
275
		/* reset rrd queues */
276
		system("rm -f /var/db/rrd/*queuedrops.rrd");
277
		system("rm -f /var/db/rrd/*queues.rrd");
278
		enable_rrd_graphing();
279

    
280
		clear_subsystem_dirty('shaper');
281

    
282
		if ($queue) {
283
			$sform = $queue->build_form();
284
			$dontshow = false;
285
		} else {
286
			$sform = $default_shaper_message;
287
			$dontshow = true;
288
		}
289
	} else if ($queue) {
290
		$queue->validate_input($_POST, $input_errors);
291
		if (!$input_errors) {
292
			$queue->update_altq_queue_data($_POST);
293
			$queue->wconfig();
294
			if (write_config("Traffic Shaper: Changed queue")) {
295
				mark_subsystem_dirty('shaper');
296
			}
297
			$dontshow = false;
298
		}
299
		read_altq_config();
300
		$sform = $queue->build_form();
301
	} else	{
302
		$dfltmsg = true;
303
		$dontshow = true;
304
	}
305
	mwexec("/usr/bin/killall -q qstats");
306
}
307

    
308
if (!$_POST && !$_GET) {
309
	$dfltmsg = true;
310
	$dontshow = true;
311
}
312

    
313
if ($queue) {
314
	if ($queue->GetEnabled()) {
315
		$can_enable = true;
316
	} else {
317
		$can_enable = false;
318
	}
319
	if ($queue->CanHaveChildren() && $can_enable) {
320
		if ($altq->GetQname() <> $queue->GetQname() && $queue->GetDefault() <> "") {
321
			$can_add = false;
322
		} else {
323
			$can_add = true;
324
		}
325
	} else {
326
		$can_add = false;
327
	}
328
}
329

    
330
include("head.inc");
331

    
332
$tree = '<ul class="tree" >';
333
if (is_array($altq_list_queues)) {
334
	foreach ($altq_list_queues as $tmpaltq) {
335
		$tree .= $tmpaltq->build_tree();
336
	}
337
	$tree .= get_interface_list_to_show();
338
}
339

    
340
$tree .= "</ul>";
341

    
342
if ($queue) {
343
	print($queue->build_javascript());
344
}
345

    
346
print($newjavascript);
347

    
348
if ($input_errors) {
349
	print_input_errors($input_errors);
350
}
351

    
352
if ($no_write_config_msg) {
353
	print_info_box($no_write_config_msg, 'danger');
354
}
355

    
356
if ($changes_applied) {
357
	print_apply_result_box($retval);
358
}
359

    
360
if (is_subsystem_dirty('shaper')) {
361
	print_apply_box(gettext("The traffic shaper configuration has been changed.") . "<br />" . gettext("The changes must be applied for them to take effect."));
362
}
363

    
364
$tab_array = array();
365
$tab_array[] = array(gettext("By Interface"), true, "firewall_shaper.php");
366
$tab_array[] = array(gettext("By Queue"), false, "firewall_shaper_queues.php");
367
$tab_array[] = array(gettext("Limiters"), false, "firewall_shaper_vinterface.php");
368
$tab_array[] = array(gettext("Wizards"), false, "firewall_shaper_wizards.php");
369
display_top_tabs($tab_array);
370

    
371
?>
372
<script type="text/javascript" src="./vendor/tree/tree.js"></script>
373

    
374
<div class="table-responsive">
375
	<table class="table">
376
		<tbody>
377
			<tr class="tabcont">
378
				<td class="col-md-1">
379
<?php
380
// Display the shaper tree
381
print($tree);
382

    
383
if (count($altq_list_queues) > 0) {
384
?>
385
					<a href="firewall_shaper.php?action=resetall" class="btn btn-sm btn-danger">
386
						<i class="fa-solid fa-trash-can icon-embed-btn"></i>
387
						<?=gettext('Remove Shaper')?>
388
					</a>
389
<?php
390
}
391
?>
392
				</td>
393
				<td>
394
<?php
395

    
396
if (!$dfltmsg && $sform)  {
397
	// Add global buttons
398
	if (!$dontshow || $newqueue) {
399
		if ($can_add || $addnewaltq) {
400
			if ($queue) {
401
				$url = 'firewall_shaper.php?interface='. $interface . '&queue=' . $queue->GetQname() . '&action=add';
402
			} else {
403
				$url = 'firewall_shaper.php?interface='. $interface . '&action=add';
404
			}
405

    
406
			$sform->addGlobal(new Form_Button(
407
				'add',
408
				'Add new Queue',
409
				$url,
410
				'fa-solid fa-plus'
411
			))->addClass('btn-success');
412

    
413
		}
414

    
415
		if ($queue) {
416
			$url = 'firewall_shaper.php?interface='. $interface . '&queue=' . $queue->GetQname() . '&action=delete';
417
		} else {
418
			$url = 'firewall_shaper.php?interface='. $interface . '&action=delete';
419
		}
420

    
421
		$sform->addGlobal(new Form_Button(
422
			'delete',
423
			$queue ? 'Delete this queue':'Disable shaper on interface',
424
			$url,
425
			'fa-solid fa-trash-can'
426
		))->addClass('btn-danger nowarn');
427

    
428
	}
429

    
430
	print($sform);
431
}
432
?>
433
				</td>
434
			</tr>
435
		</tbody>
436
	</table>
437
</div>
438

    
439
<?php if (empty(get_interface_list_to_show()) && (!is_array($altq_list_queues) || (count($altq_list_queues) == 0))): ?>
440
<div>
441
	<div class="infoblock blockopen">
442
		<?php print_info_box(gettext("This firewall does not have any interfaces assigned that are capable of using ALTQ traffic shaping."), 'danger', false); ?>
443
	</div>
444
</div>
445
<?php endif; ?>
446

    
447
<?php
448
if ($dfltmsg) {
449
?>
450
<div>
451
	<div class="infoblock">
452
		<?php print_info_box($default_shaper_msg, 'info', false); ?>
453
	</div>
454
</div>
455
<?php
456
}
457
include("foot.inc");
(56-56/230)