r1892 + introduce and make use of getWhereClause()
[racktables] / inc / interface.php
CommitLineData
b325120a 1<?php
e673ee24
DO
2/*
3*
4* This file contains frontend functions for RackTables.
5*
6*/
7
9c0b0016
DO
8// Interface function's special.
9$nextorder['odd'] = 'even';
10$nextorder['even'] = 'odd';
11
e673ee24
DO
12// Main menu.
13function renderIndex ()
14{
15 global $root;
16?>
17<table border=0 cellpadding=0 cellspacing=0 width='100%'>
18 <tr>
19 <td>
20 <div style='text-align: center; margin: 10px; '>
21 <table width='100%' cellspacing=0 cellpadding=30 class=mainmenu border=0>
22 <tr>
23 <td>
b325120a
DO
24 <h1><a href='<?php echo $root; ?>?page=rackspace'>Rackspace<br>
25 <?php printImageHREF ('rackspace'); ?></a></h1>
e673ee24
DO
26 </td>
27 <td>
b325120a
DO
28 <h1><a href='<?php echo $root; ?>?page=objects'>Objects<br>
29 <?php printImageHREF ('objects'); ?></a></h1>
e673ee24
DO
30 </td>
31 <td>
b325120a
DO
32 <h1><a href='<?php echo $root; ?>?page=ipv4space'>IPv4 space<br>
33 <?php printImageHREF ('ipv4space'); ?></a></h1>
e673ee24
DO
34 </td>
35 </tr>
36 </table>
37 <table width='100%' cellspacing=0 cellpadding=30 class=mainmenu border=0>
38 <tr>
39 <td>
b325120a
DO
40 <h1><a href='<?php echo $root; ?>?page=config'>Configuration<br>
41 <?php printImageHREF ('config'); ?></a></h1>
e673ee24
DO
42 </td>
43 <td>
da95280e 44 <h1><a href='<?php echo $root; ?>?page=reports'>Reports<br>
b325120a 45 <?php printImageHREF ('reports'); ?></a></h1>
e673ee24 46 </td>
ae545907 47 <td>
f973f491
DO
48 <h1><a href='<?php echo $root; ?>?page=ipv4slb'>IPv4 SLB<br>
49 <?php printImageHREF ('ipv4slb'); ?></a></h1>
ae545907 50 </td>
e673ee24
DO
51 </tr>
52 </table>
53 </div>
54 </td>
55 </tr>
56</table>
b325120a 57<?php
e673ee24
DO
58}
59
60function renderRackspace ()
61{
489a7502
DO
62 $tagfilter = isset ($_REQUEST['tagfilter']) ? $_REQUEST['tagfilter'] : array();
63 $tagfilter = complementByKids ($tagfilter);
64 echo "<table class=objview border=0 width='100%'><tr><td class=pcleft>";
65 renderTagFilterPortlet ($tagfilter, 'rack');
66 echo '</td><td class=pcright>';
67 echo '<table border=0 cellpadding=10 cellpadding=1>';
e673ee24 68 // generate thumb gallery
489a7502 69 $rackrowList = getRackspace ($tagfilter);
9c0b0016
DO
70 global $root, $nextorder;
71 $rackwidth = getConfigVar ('rtwidth_0') + getConfigVar ('rtwidth_1') + getConfigVar ('rtwidth_2');
e673ee24
DO
72 $order = 'odd';
73 foreach ($rackrowList as $rackrow)
74 {
75 echo "<tr class=row_${order}><th><a href='${root}?page=row&row_id=${rackrow['dict_key']}'>${rackrow['dict_value']}</a></th>";
76 $rackList = getRacksForRow ($rackrow['dict_key']);
77 echo "<td><table border=0 cellspacing=5><tr>";
78 foreach ($rackList as $dummy => $rack)
79 {
80 echo "<td align=center><a href='${root}?page=rack&rack_id=${rack['id']}'>";
81 echo "<img border=0 width=${rackwidth} height=";
82 echo 3 + 3 + $rack['height'] * 2;
83 echo " title='${rack['height']} units'";
d2ec5490 84 echo "src='render_image.php?img=minirack&rack_id=${rack['id']}'>";
e673ee24
DO
85 echo "<br>${rack['name']}</a></td>";
86 }
87 echo "</tr></table></tr>\n";
88 $order = $nextorder[$order];
89 }
90 echo "</table>\n";
489a7502 91 echo "</td></tr></table>\n";
e673ee24
DO
92}
93
94function renderRow ($row_id)
95{
96 if ($row_id == 0)
97 {
39a6338a 98 showError ('Invalid row_id', __FUNCTION__);
e673ee24
DO
99 return;
100 }
101 if (($rowInfo = getRackRowInfo ($row_id)) == NULL)
102 {
39a6338a 103 showError ('getRackRowInfo() failed', __FUNCTION__);
e673ee24
DO
104 return;
105 }
114e50af 106 $rackList = getRacksForRow ($row_id);
e673ee24
DO
107 // Main layout starts.
108 echo "<table border=0 class=objectview cellspacing=0 cellpadding=0>";
109
110 // Left portlet with row information.
111 echo "<tr><td class=pcleft>";
51a2330f 112 startPortlet ($rowInfo['dict_value']);
e673ee24 113 echo "<table border=0 cellspacing=0 cellpadding=3 width='100%'>\n";
e673ee24
DO
114 echo "<tr><th width='50%' class=tdright>Racks:</th><td class=tdleft>${rowInfo['count']}</td></tr>\n";
115 echo "<tr><th width='50%' class=tdright>Units:</th><td class=tdleft>${rowInfo['sum']}</td></tr>\n";
114e50af
DO
116 echo "<tr><th width='50%' class=tdright>Utilization:</th><td class=tdleft>";
117 renderProgressBar (getRSUforRackRow ($rackList));
118 echo "</td></tr>\n";
e673ee24
DO
119 echo "</table><br>\n";
120 finishPortlet();
121
122 echo "</td><td class=pcright>";
123
9c0b0016
DO
124 global $root, $nextorder;
125 $rackwidth = getConfigVar ('rtwidth_0') + getConfigVar ('rtwidth_1') + getConfigVar ('rtwidth_2');
e673ee24
DO
126 $order = 'odd';
127 startPortlet ('Racks');
128 echo "<table border=0 cellspacing=5 align='center'><tr>";
129 foreach ($rackList as $dummy => $rack)
130 {
131 echo "<td align=center class=row_${order}><a href='${root}?page=rack&rack_id=${rack['id']}'>";
9c0b0016
DO
132 echo "<img border=0 width=" . $rackwidth * getConfigVar ('ROW_SCALE') . " height=";
133 echo (3 + 3 + $rack['height'] * 2) * getConfigVar ('ROW_SCALE');
e673ee24 134 echo " title='${rack['height']} units'";
d2ec5490 135 echo "src='render_image.php?img=minirack&rack_id=${rack['id']}'>";
e673ee24
DO
136 echo "<br>${rack['name']}</a></td>";
137 $order = $nextorder[$order];
138 }
139 echo "</tr></table>\n";
140 finishPortlet();
141
142 echo "</td></tr></table>";
143}
144
39a6338a 145function showError ($info = '', $funcname = 'N/A')
e673ee24
DO
146{
147 global $root;
b1cae282 148 echo "<div class=msg_error>An error has occured in function [${funcname}]. ";
e673ee24
DO
149 if (empty ($info))
150 echo 'No additional information is available.';
151 else
152 echo "Additional information:<br><p>\n<pre>\n${info}\n</pre></p>";
153 echo "Go back or try starting from <a href='${root}'>index page</a>.<br></div>\n";
154}
155
156// This function renders rack as HTML table.
157function renderRack ($rack_id = 0, $hl_obj_id = 0)
158{
159 if ($rack_id == 0)
160 {
39a6338a 161 showError ('Invalid rack_id', __FUNCTION__);
e673ee24
DO
162 return;
163 }
164 if (($rackData = getRackData ($rack_id)) == NULL)
165 {
39a6338a 166 showError ('getRackData() failed', __FUNCTION__);
e673ee24
DO
167 return;
168 }
169 global $root, $pageno, $tabno;
170 markAllSpans ($rackData);
171 if ($hl_obj_id > 0)
172 highlightObject ($rackData, $hl_obj_id);
173 markupObjectProblems ($rackData);
174 $prev_id = getPrevIDforRack ($rackData['row_id'], $rack_id);
175 $next_id = getNextIDforRack ($rackData['row_id'], $rack_id);
d48d8820
DO
176 echo "<center><table border=0><tr valign=middle>";
177 echo "<td><h2><a href='${root}?page=row&row_id=${rackData['row_id']}'>${rackData['row_name']}</a> :</h2></td>";
e673ee24
DO
178 // FIXME: use 'bypass'?
179 if ($prev_id != NULL)
9803c56c 180 {
d48d8820 181 echo "<td><a href='${root}?page=rack&rack_id=${prev_id}'>";
9803c56c 182 printImageHREF ('prev', 'previous rack');
d48d8820 183 echo "</a></td>";
9803c56c 184 }
d48d8820 185 echo "<td><h2><a href='${root}?page=rack&rack_id=${rackData['id']}'>${rackData['name']}</a></h2></td>";
e673ee24 186 if ($next_id != NULL)
9803c56c 187 {
d48d8820 188 echo "<td><a href='${root}?page=rack&rack_id=${next_id}'>";
f444c095 189 printImageHREF ('next', 'next rack');
d48d8820 190 echo "</a></td>";
9803c56c 191 }
d48d8820 192 echo "</h2></td></tr></table>\n";
1c81a02c
DO
193 if ($rackData['left_is_front'] == 'yes')
194 $markup = array ('left' => 'Front', 'right' => 'Back');
195 else
196 $markup = array ('left' => 'Back', 'right' => 'Front');
e673ee24 197 echo "<table class=rack border=0 cellspacing=0 cellpadding=1>\n";
9ddfe309
DO
198 echo "<tr><th width='10%'>&nbsp;</th><th width='20%'>${markup['left']}</th>";
199 echo "<th width='50%'>Interior</th><th width='20%'>${markup['right']}</th></tr>\n";
e673ee24
DO
200 for ($i = $rackData['height']; $i > 0; $i--)
201 {
9ddfe309 202 echo '<tr><th>' . ($rackData['bottom_is_unit1'] == 'yes' ? $i : $rackData['height'] - $i + 1) . '</th>';
e673ee24
DO
203 for ($locidx = 0; $locidx < 3; $locidx++)
204 {
205 if (isset ($rackData[$i][$locidx]['skipped']))
206 continue;
207 $state = $rackData[$i][$locidx]['state'];
208 echo "<td class=state_${state}";
209 if (isset ($rackData[$i][$locidx]['hl']))
210 echo $rackData[$i][$locidx]['hl'];
211 if (isset ($rackData[$i][$locidx]['colspan']))
212 echo ' colspan=' . $rackData[$i][$locidx]['colspan'];
213 if (isset ($rackData[$i][$locidx]['rowspan']))
214 echo ' rowspan=' . $rackData[$i][$locidx]['rowspan'];
215 echo ">";
216 switch ($state)
217 {
218 case 'T':
219 $objectData = getObjectInfo ($rackData[$i][$locidx]['object_id']);
220 if (!empty ($objectData['asset_no']))
221 $prefix = "<div title='${objectData['asset_no']}";
222 else
223 $prefix = "<div title='no asset tag";
224 // Don't tell about label, if it matches common name.
225 if ($objectData['name'] != $objectData['label'] and !empty ($objectData['label']))
226 $suffix = ", visible label is \"${objectData['label']}\"'>";
227 else
228 $suffix = "'>";
229 echo $prefix . $suffix;
230 echo "<a href='${root}?page=object&object_id=${objectData['id']}'>${objectData['dname']}</a></div>";
231 break;
232 case 'A':
233 echo '<div title="This rackspace does not exist">&nbsp;</div>';
234 break;
235 case 'F':
236 echo '<div title="Free rackspace">&nbsp;</div>';
237 break;
238 case 'U':
239 echo '<div title="Problematic rackspace, you CAN\'T mount here">&nbsp;</div>';
240 break;
241 default:
242 echo '<div title="No data">&nbsp;</div>';
243 break;
244 }
245 echo '</td>';
246 }
247 echo "</tr>\n";
248 }
249 echo "</table></center>\n";
250}
251
252function renderNewObjectForm ()
253{
254 global $pageno, $tabno;
255
256 // Look for current submit.
257 if (isset ($_REQUEST['got_data']))
258 {
259 $log = array();
2c6c7645
DO
260 assertUIntArg ('object_type_id', __FUNCTION__);
261 assertStringArg ('object_name', __FUNCTION__, TRUE);
262 assertStringArg ('object_label', __FUNCTION__, TRUE);
263 assertStringArg ('object_barcode', __FUNCTION__, TRUE);
264 assertStringArg ('object_asset_no', __FUNCTION__, TRUE);
e673ee24
DO
265 $type_id = $_REQUEST['object_type_id'];
266 $name = $_REQUEST['object_name'];
267 $label = $_REQUEST['object_label'];
268 $asset_no = $_REQUEST['object_asset_no'];
269 $barcode = $_REQUEST['object_barcode'];
270
271 if (commitAddObject ($name, $label, $barcode, $type_id, $asset_no) === TRUE)
272 $log[] = array ('code' => 'success', 'message' => "Added new object '${name}'");
273 else
4d2e93f2 274 $log[] = array ('code' => 'error', 'message' => __FUNCTION__ . ': commitAddObject() failed');
e673ee24
DO
275 printLog ($log);
276 }
277
278 // Render a form for the next.
279 startPortlet ('Object attributes');
280 echo '<form>';
281 echo "<input type=hidden name=page value=${pageno}>";
282 echo "<input type=hidden name=tab value=${tabno}>";
283 echo '<table border=0 align=center>';
284 echo "<tr><th class=tdright>Type:</th><td class=tdleft>";
a477e405
DO
285 $typelist = getObjectTypeList();
286 $typelist[0] = 'select type...';
287 printSelect ($typelist, 'object_type_id', getConfigVar ('DEFAULT_OBJECT_TYPE'));
e673ee24
DO
288 echo "</td></tr>\n";
289 echo "<tr><th class=tdright>Common name:</th><td class=tdleft><input type=text name=object_name></td></tr>\n";
290 echo "<tr><th class=tdright>Visible label:</th><td class=tdleft><input type=text name=object_label></td></tr>\n";
291 echo "<tr><th class=tdright>Asset tag:</th><td class=tdleft><input type=text name=object_asset_no></td></tr>\n";
292 echo "<tr><th class=tdright>Barcode:</th><td class=tdleft><input type=text name=object_barcode></td></tr>\n";
293 echo "<tr><td class=submit colspan=2><input type=submit name=got_data value='Create'></td></tr>\n";
294 echo '</form></table>';
295 finishPortlet();
296}
297
298function renderNewRackForm ($row_id)
299{
300 global $pageno, $tabno;
301
302 // Look for current submit.
303 if (isset ($_REQUEST['got_data']))
304 {
305 $log = array();
2c6c7645
DO
306 assertStringArg ('rack_name', __FUNCTION__);
307 assertUIntArg ('rack_height', __FUNCTION__);
308 assertStringArg ('rack_comment', __FUNCTION__, TRUE);
e673ee24
DO
309 $name = $_REQUEST['rack_name'];
310 $height = $_REQUEST['rack_height'];
311 $comment = $_REQUEST['rack_comment'];
312
313 if (commitAddRack ($name, $height, $row_id, $comment) === TRUE)
314 $log[] = array ('code' => 'success', 'message' => "Added new rack '${name}'");
315 else
4d2e93f2 316 $log[] = array ('code' => 'error', 'message' => __FUNCTION__ . 'commitAddRack() failed');
e673ee24
DO
317 printLog ($log);
318 }
319
320 // Render a form for the next.
321 startPortlet ('Rack attributes');
322 echo '<form>';
323 echo "<input type=hidden name=page value=${pageno}>";
324 echo "<input type=hidden name=tab value=${tabno}>";
325 echo "<input type=hidden name=row_id value=${row_id}>";
326 echo '<table border=0 align=center>';
b901bf1f
DO
327 $defh = getConfigVar ('DEFAULT_RACK_HEIGHT');
328 if ($defh == 0)
329 $defh = '';
a7bc8321 330 echo "<tr><th class=tdright>Name (required):</th><td class=tdleft><input type=text name=rack_name tabindex=1></td></tr>\n";
b901bf1f 331 echo "<tr><th class=tdright>Height in units (required):</th><td class=tdleft><input type=text name=rack_height tabindex=2 value='${defh}'></td></tr>\n";
4134b5c0 332 echo "<tr><th class=tdright>Comment:</th><td class=tdleft><input type=text name=rack_comment tabindex=3></td></tr>\n";
e673ee24
DO
333 echo "<tr><td class=submit colspan=2><input type=submit name=got_data value='Create'></td></tr>\n";
334 echo '</form></table>';
335 finishPortlet();
336}
337
338function renderEditObjectForm ($object_id)
339{
340 showMessageOrError();
341 // Handle submit.
342 if (isset ($_REQUEST['got_data']))
343 {
344 $log = array();
345 // object_id is already verified by page handler
2c6c7645
DO
346 assertUIntArg ('object_type_id', __FUNCTION__);
347 assertStringArg ('object_name', __FUNCTION__, TRUE);
348 assertStringArg ('object_label', __FUNCTION__, TRUE);
349 assertStringArg ('object_barcode', __FUNCTION__, TRUE);
350 assertStringArg ('object_asset_no', __FUNCTION__, TRUE);
e673ee24
DO
351 $type_id = $_REQUEST['object_type_id'];
352 if (isset ($_REQUEST['object_has_problems']) and $_REQUEST['object_has_problems'] == 'on')
353 $has_problems = 'yes';
354 else
355 $has_problems = 'no';
356 $name = $_REQUEST['object_name'];
357 $label = $_REQUEST['object_label'];
358 $barcode = $_REQUEST['object_barcode'];
359 $asset_no = $_REQUEST['object_asset_no'];
360 $comment = $_REQUEST['object_comment'];
361
362 if (commitUpdateObject ($object_id, $name, $label, $barcode, $type_id, $has_problems, $asset_no, $comment) === TRUE)
363 $log[] = array ('code' => 'success', 'message' => "Updated object '${name}'");
364 else
4d2e93f2 365 $log[] = array ('code' => 'error', 'message' => __FUNCTION__ . ': commitUpdateObject() failed');
c7fe33be
DO
366 // Invalidate thumb cache of all racks objects could occupy.
367 foreach (getResidentRacksData ($object_id, FALSE) as $rack_id)
368 resetThumbCache ($rack_id);
e673ee24
DO
369 printLog ($log);
370 }
371
372 global $pageno, $tabno;
373 $object = getObjectInfo ($object_id);
374 if ($object == NULL)
375 {
39a6338a 376 showError ('getObjectInfo() failed', __FUNCTION__);
e673ee24
DO
377 return;
378 }
379
380 // Render a form for the next submit;
381 echo '<table border=0 width=100%><tr>';
382
383 echo '<td class=pcleft>';
384 startPortlet ('Static attributes');
250a40c5 385 echo '<form method=post>';
e673ee24
DO
386 echo "<input type=hidden name=page value=${pageno}>";
387 echo "<input type=hidden name=tab value=${tabno}>";
388 echo "<input type=hidden name=object_id value=${object_id}>";
389 echo '<table border=0 align=center>';
390 echo "<tr><th class=tdright>Type:</th><td class=tdleft>";
391 printSelect (getObjectTypeList(), 'object_type_id', $object['objtype_id']);
392 echo "</td></tr>\n";
393 // Common attributes.
394 echo "<tr><th class=tdright>Common name:</th><td class=tdleft><input type=text name=object_name value='${object['name']}'></td></tr>\n";
395 echo "<tr><th class=tdright>Visible label:</th><td class=tdleft><input type=text name=object_label value='${object['label']}'></td></tr>\n";
396 echo "<tr><th class=tdright>Asset tag:</th><td class=tdleft><input type=text name=object_asset_no value='${object['asset_no']}'></td></tr>\n";
397 echo "<tr><th class=tdright>Barcode:</th><td class=tdleft><input type=text name=object_barcode value='${object['barcode']}'></td></tr>\n";
398 echo "<tr><th class=tdright>Has problems:</th><td class=tdleft><input type=checkbox name=object_has_problems";
399 if ($object['has_problems'] == 'yes')
400 echo ' checked';
401 echo "></td></tr>\n";
402 echo "<tr><td colspan=2><b>Comment:</b><br><textarea name=object_comment rows=10 cols=80>${object['comment']}</textarea></td></tr>";
403 echo "<tr><th class=submit colspan=2><input type=submit name=got_data value='Update'></td></tr>\n";
404 echo '</form></table><br>';
405 finishPortlet();
406 echo '</td>';
407
408 // Optional attributes.
409 echo '<td class=pcright>';
410 startPortlet ('Optional attributes');
411 $values = getAttrValues ($object_id);
412 global $root;
413 echo "<table cellspacing=0 cellpadding=5 align=center class=widetable>\n";
414 echo "<tr><th>&nbsp;</th><th>Attribute</th><th>Value</th><th>&nbsp;</th></tr>\n";
0dfb8a2a
DO
415 echo "<form method=post action='${root}process.php'>\n";
416 echo "<input type=hidden name=page value=${pageno}>\n";
417 echo "<input type=hidden name=tab value=${tabno}>\n";
418 echo "<input type=hidden name=op value=upd>\n";
419 echo "<input type=hidden name=object_id value=${object_id}>\n";
420 echo '<input type=hidden name=num_attrs value=' . count($values) . ">\n";
421
422 $i = 0;
e673ee24
DO
423 foreach ($values as $record)
424 {
0dfb8a2a 425 echo "<input type=hidden name=${i}_attr_id value=${record['id']}>";
0c4605ab 426 echo '<tr><td>';
ca1fec24 427 if (!empty ($record['value']))
0c4605ab
DO
428 {
429 echo "<a href=${root}process.php?page=${pageno}&tab=${tabno}&op=del&object_id=${object_id}&attr_id=${record['id']}>";
d48d8820 430 printImageHREF ('clear', 'Clear value');
0c4605ab
DO
431 echo '</a>';
432 }
433 else
d48d8820 434 echo '&nbsp;';
0c4605ab 435 echo '</td>';
e673ee24
DO
436 echo "<td class=tdright>${record['name']}:</td><td class=tdleft>";
437 switch ($record['type'])
438 {
439 case 'uint':
440 case 'float':
441 case 'string':
0dfb8a2a 442 echo "<input type=text name=${i}_value value='${record['value']}'>";
e673ee24
DO
443 break;
444 case 'dict':
445 $chapter = readChapter ($record['chapter_name']);
4c330a14 446 $chapter[0] = '-- NOT SET --';
0dfb8a2a 447 printSelect ($chapter, "${i}_value", $record['key']);
e673ee24
DO
448 break;
449 }
0dfb8a2a
DO
450 echo "</td></tr>\n";
451 $i++;
e673ee24 452 }
0dfb8a2a
DO
453 echo "<tr><td colspan=3><input type=submit value='Update'></td></tr>\n";
454 echo "</form>";
e673ee24
DO
455 echo "</table>\n";
456 finishPortlet();
457 echo '</td>';
458
459 echo '</tr><tr>';
460
461 echo '<td colspan=2>';
462 startPortlet ('history');
463 renderHistory ($pageno, $object_id);
464 finishPortlet();
465 echo '</td>';
466
467 echo '</tr></table>';
468}
469
470// This is a clone of renderEditObjectForm().
471function renderEditRackForm ($rack_id)
472{
473 // Handle submit.
474 if (isset ($_REQUEST['got_data']))
475 {
476 $log = array();
2c6c7645
DO
477 assertUIntArg ('rack_row_id', __FUNCTION__);
478 assertUIntArg ('rack_height', __FUNCTION__);
479 assertStringArg ('rack_name', __FUNCTION__);
480 assertStringArg ('rack_comment', __FUNCTION__, TRUE);
e673ee24
DO
481 $row_id = $_REQUEST['rack_row_id'];
482 $height = $_REQUEST['rack_height'];
483 $name = $_REQUEST['rack_name'];
484 $comment = $_REQUEST['rack_comment'];
485
486 if (commitUpdateRack ($rack_id, $name, $height, $row_id, $comment) === TRUE)
487 $log[] = array ('code' => 'success', 'message' => "Updated rack '${name}'");
488 else
4d2e93f2 489 $log[] = array ('code' => 'error', 'message' => __FUNCTION__ . ': commitUpdateRack() failed');
c7fe33be 490 resetThumbCache ($rack_id);
e673ee24
DO
491 printLog ($log);
492 }
493
494 global $pageno, $tabno;
495 $rack = getRackData ($rack_id);
496 if ($rack == NULL)
497 {
39a6338a 498 showError ('getRackData() failed', __FUNCTION__);
e673ee24
DO
499 return;
500 }
501
502 // Render a form for the next.
503 startPortlet ('Rack attributes');
504 echo '<form>';
505 echo "<input type=hidden name=page value=${pageno}>";
506 echo "<input type=hidden name=tab value=${tabno}>";
507 echo "<input type=hidden name=rack_id value=${rack_id}>";
508 echo '<table border=0 align=center>';
509 echo "<tr><th class=tdright>Rack row:</th><td class=tdleft>";
4c330a14 510 printSelect (readChapter ('RackRow'), 'rack_row_id', $rack['row_id']);
e673ee24
DO
511 echo "</td></tr>\n";
512 echo "<tr><th class=tdright>Name (required):</th><td class=tdleft><input type=text name=rack_name value='${rack['name']}'></td></tr>\n";
513 echo "<tr><th class=tdright>Height (required):</th><td class=tdleft><input type=text name=rack_height value='${rack['height']}'></td></tr>\n";
514 echo "<tr><th class=tdright>Comment:</th><td class=tdleft><input type=text name=rack_comment value='${rack['comment']}'></td></tr>\n";
515 echo "<tr><td class=submit colspan=2><input type=submit name=got_data value='Update'></td></tr>\n";
516 echo '</form></table><br>';
517 finishPortlet();
518
519 startPortlet ('History');
520 renderHistory ($pageno, $rack_id);
521 finishPortlet();
522}
523
524// This is a helper for creators and editors.
525function printSelect ($rowList, $select_name, $selected_id = 1)
526{
9e7f32a7
DO
527 // First collect all data for OPTGROUPs, then ouput it and dump
528 // the rest of records as is.
529 $optgroup = array();
530 $other = array();
4c330a14 531 foreach ($rowList as $dict_key => $dict_value)
e673ee24 532 {
24cbe8af 533 if (strpos ($dict_value, '^') !== FALSE)
9e7f32a7 534 {
24cbe8af 535 $tmp = explode ('^', $dict_value, 2);
9e7f32a7
DO
536 $optgroup[$tmp[0]][$dict_key] = $tmp[1];
537 }
2613bc1c
DO
538 elseif (strpos ($dict_value, '&') !== FALSE)
539 {
540 $tmp = explode ('&', $dict_value, 2);
541 $optgroup[$tmp[0]][$dict_key] = $tmp[1];
542 }
9e7f32a7
DO
543 else
544 $other[$dict_key] = $dict_value;
545 }
546 echo "<select name=${select_name}>";
547 if (!count ($optgroup))
548 {
549 foreach ($other as $dict_key => $dict_value)
550 {
551 echo "<option value=${dict_key}";
552 if ($dict_key == $selected_id)
553 echo ' selected';
554 echo ">${dict_value}</option>";
555 }
556 }
557 else
558 {
559 foreach ($optgroup as $groupname => $groupdata)
560 {
561 echo "<optgroup label='${groupname}'>";
562 foreach ($groupdata as $dict_key => $dict_value)
563 {
564 echo "<option value=${dict_key}";
565 if ($dict_key == $selected_id)
566 echo ' selected';
567 echo ">${dict_value}</option>";
568 }
569 echo "</optgroup>\n";
570 }
571 if (count ($other))
572 {
573 echo "<optgroup label='other'>\n";
574 foreach ($other as $dict_key => $dict_value)
575 {
576 echo "<option value=${dict_key}";
577 if ($dict_key == $selected_id)
578 echo ' selected';
579 echo ">${dict_value}</option>";
580 }
581 echo "</optgroup>\n";
582 }
e673ee24
DO
583 }
584 echo "</select>";
585}
586
254673dd
DO
587// used by renderGridForm() and renderRackPage()
588function renderRackInfoPortlet ($rackData)
589{
590 startPortlet ('summary');
591 echo "<table border=0 cellspacing=0 cellpadding=3 width='100%'>\n";
592 echo "<tr><th width='50%' class=tdright>Rack row:</th><td class=tdleft>${rackData['row_name']}</td></tr>\n";
593 echo "<tr><th width='50%' class=tdright>Name:</th><td class=tdleft>${rackData['name']}</td></tr>\n";
594 echo "<tr><th width='50%' class=tdright>Height:</th><td class=tdleft>${rackData['height']}</td></tr>\n";
595 echo "<tr><th width='50%' class=tdright>Utilization:</th><td class=tdleft>";
596 renderProgressBar (getRSUforRack ($rackData));
597 echo "</td></tr>\n";
598 echo "<tr><th width='50%' class=tdright>Objects:</th><td class=tdleft>";
599 echo getObjectCount ($rackData);
600 echo "</td></tr>\n";
601 printTagTRs();
602 if (!empty ($rackData['comment']))
603 echo "<tr><th width='50%' class=tdright>Comment:</th><td class=tdleft>${rackData['comment']}</td></tr>\n";
604 echo '</table>';
605 finishPortlet();
606}
607
e673ee24 608// This is a universal editor of rack design/waste.
bb09cca0 609function renderGridForm ($rack_id = 0, $filter, $header, $submit, $state1, $state2)
e673ee24
DO
610{
611 if ($rack_id == 0)
612 {
591ff2c4 613 showError ('Invalid rack_id', __FUNCTION__);
e673ee24
DO
614 return;
615 }
616 if (($rackData = getRackData ($rack_id)) == NULL)
617 {
591ff2c4 618 showError ('getRackData() failed', __FUNCTION__);
e673ee24
DO
619 return;
620 }
621
622 global $root, $pageno, $tabno;
254673dd 623 $filter ($rackData);
e673ee24
DO
624 markupObjectProblems ($rackData);
625
626 // Process form submit.
627 if (isset ($_REQUEST['do_update']))
628 {
629 $log[] = processGridForm ($rackData, $state1, $state2);
254673dd
DO
630 printLog ($log);
631 $rackData = getRackData ($rack_id);
632 $filter ($rackData);
633 markupObjectProblems ($rackData);
e673ee24
DO
634 }
635
636 // Render the result whatever it is.
637 // Main layout.
638 echo "<table border=0 class=objectview cellspacing=0 cellpadding=0>";
639 echo "<tr><td colspan=2 align=center><h1>${rackData['name']}</h1></td></tr>\n";
640
641 // Left column with information portlet.
642 echo "<tr><td class=pcleft height='1%' width='50%'>";
254673dd 643 renderRackInfoPortlet ($rackData);
e673ee24 644 echo "</td>\n";
bb09cca0 645 echo "<td class=pcright>";
e673ee24
DO
646
647 // Grid form.
648 startPortlet ($header);
649 echo "<center>\n";
650 echo "<table class=rack border=0 cellspacing=0 cellpadding=1>\n";
651 echo "<tr><th width='10%'>&nbsp;</th><th width='20%'>Front</th>";
652 echo "<th width='50%'>Interior</th><th width='20%'>Back</th></tr>\n";
9d479d56 653 echo "<form method=post action='${root}?'>\n";
e673ee24
DO
654 echo "<input type=hidden name=page value=${pageno}>\n";
655 echo "<input type=hidden name=tab value=${tabno}>\n";
656 echo "<input type=hidden name=rack_id value=${rack_id}>\n";
657 markupAtomGrid ($rackData, $state2);
658 renderAtomGrid ($rackData);
659 echo "</table></center>\n";
660 echo "<br><input type=submit name=do_update value='${submit}'></form><br><br>\n";
661 finishPortlet();
bb09cca0 662 echo "</td></tr></table>\n";
e673ee24
DO
663}
664
665function renderRackDesign ($rack_id)
666{
bb09cca0 667 renderGridForm ($rack_id, 'applyRackDesignMask', 'Rack design', 'Set rack design', 'A', 'F');
e673ee24
DO
668}
669
670function renderRackProblems ($rack_id = 0)
671{
bb09cca0 672 renderGridForm ($rack_id, 'applyRackProblemMask', 'Rack problems', 'Mark unusable atoms', 'F', 'U');
e673ee24
DO
673}
674
675function startPortlet ($title = '')
676{
677 echo "<div class=portlet><h2>${title}</h2>";
678}
679
680function finishPortlet ()
681{
682 echo "</div>\n";
683}
684
685function printRefsOfType ($refs, $type, $eq)
686{
687 global $root;
688 $gotone=0;
689 foreach ($refs as $ref)
690 {
691 if ($eq($ref['type'], $type))
692 {
693 if ($gotone) echo ', ';
4b2bf583
DO
694 echo "<a href='${root}?page=object&object_id=${ref['object_id']}'>";
695 if (!empty ($ref['name']))
696 echo $ref['name'] . '@';
697 echo "${ref['object_name']}</a>";
e673ee24
DO
698 $gotone=1;
699 }
700 }
701}
702
703function renderRackObject ($object_id = 0)
704{
41bd8c87 705 global $root;
e673ee24
DO
706 if ($object_id <= 0)
707 {
591ff2c4 708 showError ('Invalid object_id', __FUNCTION__);
e673ee24
DO
709 return;
710 }
711 $info = getObjectInfo ($object_id);
712 if ($info == NULL)
713 {
591ff2c4 714 showError ('getObjectInfo() failed', __FUNCTION__);
e673ee24
DO
715 return;
716 }
717 // Main layout starts.
718 echo "<table border=0 class=objectview cellspacing=0 cellpadding=0>";
719 echo "<tr><td colspan=2 align=center><h1>${info['dname']}</h1></td></tr>\n";
720 // left column with uknown number of portlets
721 echo "<tr><td class=pcleft>";
722 startPortlet ('Object information');
723 echo "<table border=0 cellspacing=0 cellpadding=3 width='100%'>\n";
724 if (!empty ($info['name']))
725 echo "<tr><th width='50%' class=tdright>Common name:</th><td class=tdleft>${info['name']}</td></tr>\n";
9c0b0016 726 elseif (in_array ($info['objtype_id'], explode (',', getConfigVar ('NAMEFUL_OBJTYPES'))))
a0ec6295 727 echo "<tr><td colspan=2 class=msg_error>Common name is missing.</td></tr>\n";
e673ee24
DO
728 echo "<tr><th width='50%' class=tdright>Object type:</th><td class=tdleft>${info['objtype_name']}</td></tr>\n";
729 if (!empty ($info['asset_no']))
730 echo "<tr><th width='50%' class=tdright>Asset tag:</th><td class=tdleft>${info['asset_no']}</td></tr>\n";
a6305acc 731 elseif (in_array ($info['objtype_id'], explode (',', getConfigVar ('REQUIRE_ASSET_TAG_FOR'))))
a0ec6295 732 echo "<tr><td colspan=2 class=msg_error>Asset tag is missing.</td></tr>\n";
e673ee24
DO
733 if (!empty ($info['label']))
734 echo "<tr><th width='50%' class=tdright>Visible label:</th><td class=tdleft>${info['label']}</td></tr>\n";
735 if (!empty ($info['barcode']))
736 echo "<tr><th width='50%' class=tdright>Barcode:</th><td class=tdleft>${info['barcode']}</td></tr>\n";
737 if ($info['has_problems'] == 'yes')
738 echo "<tr><td colspan=2 class=msg_error>Has problems</td></tr>\n";
24cbe8af 739 foreach (getAttrValues ($object_id, TRUE) as $record)
e673ee24 740 if (!empty ($record['value']))
50a954f6 741 echo "<tr><th width='50%' class=opt_attr_th>${record['name']}:</th><td class=tdleft>${record['a_value']}</td></tr>\n";
41bd8c87 742 printTagTRs();
e673ee24
DO
743 echo "</table><br>\n";
744 finishPortlet();
745
746 if (!empty ($info['comment']))
747 {
748 startPortlet ('Comment');
6cc5d6cd 749 echo '<div class=commentblock>' . string_insert_hrefs ($info['comment']) . '</div>';
e673ee24
DO
750 finishPortlet ();
751 }
752
753 $ports = getObjectPortsAndLinks ($object_id);
754 if (count ($ports))
755 {
756 startPortlet ('Ports and links');
757 usort($ports, 'sortByName');
758 if ($ports)
759 {
760 $hl_port_id = 0;
761 if (isset ($_REQUEST['hl_port_id']))
762 {
2c6c7645 763 assertUIntArg ('hl_port_id', __FUNCTION__);
e673ee24
DO
764 $hl_port_id = $_REQUEST['hl_port_id'];
765 }
766 echo "<table cellspacing=0 cellpadding='5' align='center' class='widetable'>\n";
767 echo "<tr><th>Local name</th><th>Visible label</th><th>Port type</th><th>L2 address</th>";
768 echo "<th>Rem. Object</th><th>Rem. port</th></tr>\n";
769 foreach ($ports as $port)
770 {
771 echo '<tr';
772 if ($hl_port_id == $port['id'])
773 echo ' class=port_highlight';
774 echo "><td>${port['name']}</td><td>${port['label']}</td><td>${port['type']}</td>";
775 echo "<td>${port['l2address']}</td>";
776 if ($port['remote_object_id'])
777 {
778 echo "<td><a href='${root}?page=object&object_id=${port['remote_object_id']}'>${port['remote_object_name']}</a></td>";
779 echo "<td>${port['remote_name']}</td>";
780 }
781 elseif (!empty ($port['reservation_comment']))
782 {
783 echo "<td><b>Reserved;</b></td>";
784 echo "<td>${port['reservation_comment']}</td>";
785 }
786 else
787 echo '<td>&nbsp;</td><td>&nbsp;</td>';
788 echo "</tr>\n";
789 }
790 echo "</table><br>\n";
791 }
792 finishPortlet();
793 }
794 $addresses = getObjectAddresses ($object_id);
795 usort($addresses, 'sortAddresses');
796 if (count ($addresses))
797 {
f28fbe8b 798 startPortlet ('IPv4 addresses');
e673ee24
DO
799 echo "<table cellspacing=0 cellpadding='5' align='center' class='widetable'>\n";
800 echo "<tr><th>Interface name</th><th>IP Address</th><th>Description</th><th>Misc</th></tr>\n";
801 foreach ($addresses as $addr)
802 {
803 if (strlen($addr['address_name'])>40)
804 $address_name = substr($addr['address_name'],0,38).'...';
805 else
806 $address_name = $addr['address_name'];
807
808 $virtnum = countRefsOfType($addr['references'], 'virtual', 'eq');
809 $sharednum = countRefsOfType($addr['references'], 'shared', 'eq');
810 $regnum = countRefsOfType($addr['references'], 'regular', 'eq');
811 $notvirtnum = countRefsOfType($addr['references'], 'virtual', 'neq');
812
813 if ($addr['address_reserved']=='yes')
24e85a1a 814 $class='trerror';
e673ee24 815 elseif ($addr['type']!='virtual' && $regnum>0)
24e85a1a 816 $class='trerror';
e673ee24 817 elseif ($addr['type']=='regular' && $sharednum>0)
24e85a1a 818 $class='trerror';
e673ee24
DO
819 else
820 $class='';
821
cf50bfff 822 echo "<tr class='$class'><td class=tdleft>${addr['name']}</td><td class=tdleft><a href='${root}?page=ipaddress&ip=${addr['ip']}'>${addr['ip']}</a></td><td class='description'>$address_name</td><td class=tdleft>\n";
e673ee24
DO
823
824 if ($addr['address_reserved']=='yes')
825 echo "<b>Reserved;</b> ";
826
827 if ($addr['type'] == 'virtual')
828 {
829 echo "<b>V</b>";
830 if ($notvirtnum > 0)
831 {
832 echo " Owners: ";
833 printRefsOfType($addr['references'], 'virtual', 'neq');
834 }
835 }
836 elseif ($addr['type'] == 'shared')
837 {
838 echo "<b>S</b>";
839 if ($sharednum > 0)
840 {
841 echo " Peers: ";
842 printRefsOfType($addr['references'], 'shared', 'eq');
843 echo ";";
844 }
845 if ($virtnum > 0)
846 {
847 echo " Virtuals: ";
848 printRefsOfType($addr['references'], 'virtual', 'eq');
849 echo ";";
850 }
851 if ($regnum > 0)
852 {
853 echo " Collisions: ";
854 printRefsOfType($addr['references'], 'regular', 'eq');
855 }
856
857 }
858 else
859 {
860 if ($virtnum > 0)
861 {
862 echo " Virtuals: ";
863 printRefsOfType($addr['references'], 'virtual', 'eq');
864 echo ";";
865 }
866 if ($notvirtnum > 0)
867 {
868 echo " Collisions: ";
869 printRefsOfType($addr['references'], 'virtual', 'neq');
870 }
871 }
872
873 echo "</td></tr>\n";
874 }
875 echo "</table><br>\n";
876 finishPortlet();
877 }
878
eeb4a5d8 879 $forwards = getNATv4ForObject ($object_id);
e673ee24
DO
880 if (count($forwards['in']) or count($forwards['out']))
881 {
f28fbe8b 882 startPortlet('NATv4');
e673ee24
DO
883
884 if (count($forwards['out']))
885 {
886
f28fbe8b 887 echo "<h3>locally performed NAT</h3>";
e673ee24
DO
888
889 echo "<table class='widetable' cesspadding=5 cellspacing=0 border=0 align='center'>\n";
f28fbe8b 890 echo "<tr><th>Proto</th><th>Match endpoint</th><th>Translate to</th><th>Target object</th><th>Rule comment</th></tr>\n";
e673ee24
DO
891
892 foreach ($forwards['out'] as $pf)
893 {
24e85a1a 894 $class='trerrorg';
e673ee24
DO
895 $name='';
896 foreach ($addresses as $addr)
897 if ($addr['ip'] == $pf['localip'])
898 {
899 $class='';
900 $name=$addr['name'];
901 break;
902 }
903
904 echo "<tr class='$class'>";
905
f28fbe8b 906 echo "<td>${pf['proto']}</td><td class=tdleft>${name}: <a href='${root}?page=ipaddress&tab=default&ip=${pf['localip']}'>${pf['localip']}</a>:${pf['localport']}</td>";
e673ee24 907
f28fbe8b 908 echo "<td class=tdleft><a href='${root}?page=ipaddress&tab=default&ip=${pf['remoteip']}'>${pf['remoteip']}</a>:${pf['remoteport']}</td>";
e673ee24
DO
909
910 $address=getIPAddress($pf['remoteip']);
911
912 echo "<td class='description'>";
f28fbe8b
DO
913 if (count ($address['bonds']))
914 foreach($address['bonds'] as $bond)
915 echo "<a href='${root}?page=object&tab=default&object_id=${bond['object_id']}'>${bond['object_name']}(${bond['name']})</a> ";
916 elseif (!empty ($pf['remote_addr_name']))
917 echo '(' . $pf['remote_addr_name'] . ')';
e673ee24
DO
918
919 echo "</td><td class='description'>${pf['description']}</td>";
920
921 echo "</tr>";
922 }
923 echo "</table><br><br>";
924 }
925 if (count($forwards['in']))
926 {
f28fbe8b 927 echo "<h3>arriving NAT connections</h3>";
e673ee24
DO
928
929 echo "<table class='widetable' cesspadding=5 cellspacing=0 border=0 align='center'>\n";
f28fbe8b 930 echo "<tr><th>Matched endpoint</th><th>Source object</th><th>Translated to</th><th>Rule comment</th></tr>\n";
e673ee24
DO
931
932 foreach ($forwards['in'] as $pf)
933 {
934 echo "<tr>";
935 echo "<td>${pf['proto']}/<a href='${root}?page=ipaddress&tab=default&ip=${pf['localip']}'>${pf['localip']}</a>:${pf['localport']}</td>";
936
937 echo "<td class='description'><a href='${root}?page=object&tab=default&object_id=${pf['object_id']}'>${pf['object_name']}</a>";
938
939 echo "</td><td><a href='${root}?page=ipaddress&tab=default&ip=${pf['remoteip']}'>${pf['remoteip']}</a>:${pf['remoteport']}</td>";
940 echo "<td class='description'>${pf['description']}</td></tr>";
941 }
942
943 echo "</table><br><br>";
944 }
945 finishPortlet();
946 }
947
78e7b769
DO
948 $pools = getRSPoolsForObject ($object_id);
949 if (count ($pools))
950 {
951 startPortlet ('Real server pools');
952 echo "<table cellspacing=0 cellpadding=5 align=center class=widetable>\n";
732e4578 953 echo "<tr><th>VS</th><th>RS pool</th><th>RS</th><th>VS config</th><th>RS config</th></tr>\n";
748805bf 954 foreach ($pools as $vs_id => $info)
78e7b769 955 {
732e4578 956 echo "<tr valign=top><td class=tdleft><a href='${root}?page=vservice&id=${vs_id}'>";
748805bf
DO
957 echo buildVServiceName ($info);
958 echo '</a>';
959 if (!empty ($info['name']))
960 echo " (${info['name']})";
c0ae6968 961 echo "</td><td class=tdleft><a href='${root}?page=rspool&pool_id=${info['pool_id']}'>";
748805bf 962 echo (empty ($info['pool_name']) ? 'ANONYMOUS' : $info['pool_name']);
732e4578
DO
963 echo '</a></td><td class=tdleft>' . $info['rscount'] . '</td>';
964 echo "<td class=tdleft><pre>${info['vsconfig']}</pre></td>";
965 echo "<td class=tdleft><pre>${info['rsconfig']}</pre></td>";
78e7b769
DO
966 echo "</tr>\n";
967 }
968 echo "</table>\n";
969 finishPortlet();
970 }
e673ee24
DO
971 echo "</td>\n";
972
973 // After left column we have (surprise!) right column with rackspace portled only.
974 echo "<td class=pcright>";
975 // rackspace portlet
976 startPortlet ('Rackspace allocation');
977 // FIXME: now we call getRackData() twice
978 $racks = getResidentRacksData ($object_id);
979 foreach ($racks as $rackData)
980 renderRack ($rackData['id'], $object_id);
981 echo '<br>';
982 finishPortlet();
983 echo "</td></tr>";
984 echo "</table>\n";
985}
986
987function renderRackMultiSelect ($sname, $racks, $selected)
988{
9c0b0016 989 echo "<select name=${sname} multiple size=" . getConfigVar ('MAXSELSIZE') . " onchange='getElementById(\"racks\").submit()'>\n";
e673ee24
DO
990 foreach ($racks as $rack)
991 {
992 echo "<option value=${rack['id']}";
993 if (!(array_search ($rack['id'], $selected) === FALSE))
994 echo ' selected';
6a3a37b2 995 echo">${rack['row_name']}: ${rack['name']}</option>\n";
e673ee24
DO
996 }
997 echo "</select>\n";
998}
999
1000function showMessageOrError ()
1001{
1002 if (isset($_REQUEST['message']))
1003 echo "<div class=msg_success>${_REQUEST['message']}</div>";
1004 if (isset($_REQUEST['error']))
1005 echo "<div class=msg_error>${_REQUEST['error']}</div>";
1006}
1007
1008// This function renders a form for port edition.
1009function renderPortsForObject ($object_id = 0)
1010{
1011 global $root, $pageno, $tabno;
1012 if ($object_id <= 0)
1013 {
591ff2c4 1014 showError ('Invalid object_id', __FUNCTION__);
e673ee24
DO
1015 return;
1016 }
1017 showMessageOrError();
1018 startPortlet ('Ports and interfaces');
1019 $ports = getObjectPortsAndLinks ($object_id);
1020 usort($ports, 'sortByName');
1021 echo "<table cellspacing=0 cellpadding='5' align='center' class='widetable'>\n";
1022 echo "<tr><th>&nbsp;</th><th>Local name</th><th>Visible label</th><th>Port type</th><th>L2 address</th>";
1023 echo "<th>Rem. object</th><th>Rem. port</th><th>(Un)link or (un)reserve</th><th>&nbsp;</th></tr>\n";
1024 foreach ($ports as $port)
1025 {
1026 echo "<form action='${root}process.php'>";
1027 echo "<input type=hidden name=op value=editPort>";
1028 echo "<input type=hidden name=page value='${pageno}'>\n";
1029 echo "<input type=hidden name=tab value='${tabno}'>\n";
1030 echo "<input type=hidden name=port_id value='${port['id']}'>";
1031 echo "<input type=hidden name=object_id value='$object_id'>\n";
1032 echo "<tr><td><a href='${root}process.php?op=delPort&page=${pageno}&tab=${tabno}&port_id=${port['id']}&object_id=$object_id&port_name=${port['name']}'>";
1033 printImageHREF ('delete', 'Unlink and Delete this port');
1034 echo "</a></td>\n";
1035 echo "<td><input type=text name=name value='${port['name']}' size=8></td>";
1036 echo "<td><input type=text name=label value='${port['label']}' size=24></td>";
1037 echo "<td>${port['type']}</td>\n";
1038 echo "<td><input type=text name=l2address value='${port['l2address']}'></td>\n";
1039 if ($port['remote_object_id'])
1040 {
1041 echo "<td><a href='${root}?page=object&object_id=${port['remote_object_id']}'>${port['remote_object_name']}</a></td>";
1042 echo "<td>${port['remote_name']}</td>";
1043 echo "<td><a href='${root}process.php?op=unlinkPort&page=${pageno}&tab=${tabno}&port_id=${port['id']}&object_id=$object_id&port_name=";
1044 echo urlencode ($port['name']);
1045 echo "&remote_port_name=${port['remote_name']}&remote_object_name=${port['remote_object_name']}'>";
1046 printImageHREF ('unlink', 'Unlink this port');
1047 echo "</a></td>";
1048 }
1049 elseif (!empty ($port['reservation_comment']))
1050 {
1051 echo "<td><b>Reserved;</b></td>";
1052 echo "<td><input type=text name=reservation_comment value='${port['reservation_comment']}'></td>";
1053 echo "<td><a href='${root}process.php?op=useup&page=${pageno}&tab=${tabno}&port_id=${port['id']}&object_id=${object_id}'>";
1054 printImageHREF ('useup', 'Use up this port');
1055 echo "</a></td>";
1056 }
1057 else
1058 {
1059 echo "<td>&nbsp;</td><td>&nbsp;</td>";
1060 echo "<td>";
1061 echo "<a href='javascript:;' onclick='window.open(\"${root}link_helper.php?port=${port['id']}&type=${port['type_id']}&object_id=$object_id&port_name=";
1062 echo urlencode ($port['name']);
1063 echo "\",\"findlink\",\"height=700, width=400, location=no, menubar=no, resizable=yes, scrollbars=no, status=no, titlebar=no, toolbar=no\");'>";
1064 printImageHREF ('link', 'Link this port');
1065 echo "</a> <input type=text name=reservation_comment>";
1066 echo "</td>\n";
1067 }
1068 echo "<td><input type='submit' value='OK'></td>";
1069 echo "</form></tr>\n";
1070 }
d48d8820
DO
1071 echo "<form action='${root}process.php'><tr><td>";
1072 printImageHREF ('add', '', TRUE, 104);
1073 echo "</td><td><input type=text size=8 name=port_name tabindex=100></td>\n";
e673ee24
DO
1074 echo "<td><input type=text size=24 name=port_label tabindex=101></td>";
1075 echo "<input type=hidden name=op value=addPort>\n";
1076 echo "<input type=hidden name=object_id value='${object_id}'>\n";
1077 echo "<input type=hidden name=page value='${pageno}'>\n";
1078 echo "<input type=hidden name=tab value='${tabno}'>\n";
1079 echo "<td><select name='port_type_id' tabindex=102>\n";
1080 $types = getPortTypes();
9c0b0016 1081 $default_port_type = getConfigVar ('default_port_type');
e673ee24
DO
1082 foreach ($types as $typeid => $typename)
1083 {
1084 echo "<option value='${typeid}'";
1085 if ($typeid == $default_port_type)
1086 echo " selected";
1087 echo ">${typename}</option>\n";
1088 }
1089 echo "</select></td>";
1090 echo "<td><input type=text name=port_l2address tabindex=103></td>\n";
d48d8820 1091 echo "<td colspan=4>&nbsp;</td></tr></form>";
e673ee24
DO
1092 echo "</table><br>\n";
1093 finishPortlet();
1094
1095 startPortlet ('Add/update multiple ports');
1096 echo "<form action=${root}process.php method=post>";
1097 echo "<input type=hidden name=page value='${pageno}'>\n";
1098 echo "<input type=hidden name=tab value='${tabno}'>\n";
1099 echo "<input type=hidden name=object_id value='${object_id}'>\n";
1100 echo "<input type=hidden name=op value=addMultiPorts>";
1101 echo 'Format: <select name=format>';
1102 echo '<option value=c2900 disabled>Cisco 2900 series: sh int eth</option>';
1103 echo '<option value=c3600eth disabled>Cisco 3600 ethernet: sh arp | inc -</option>';
1104 echo '<option value=c3600asy>Cisco 3600 async: sh line | inc TTY</option>';
1105 echo '<option value=fiwg selected>Foundry ServerIron/FastIron WorkGroup/Edge: sh int br</option>';
1106 echo '<option value=fiedge disabled>Foundry FastIron Edge: sh int br</option>';
1107 echo '<option value=fisxii>Foundry FastIron SuperX/II4000: sh int br</option>';
351d4dbf 1108 echo '<option value=ssv1>SSV:&lt;interface name&gt; &lt;MAC address&gt;</option>';
e673ee24
DO
1109 echo "</select>";
1110 echo 'Default port type: ';
1111 echo "<select name=port_type>\n";
1112 foreach ($types as $typeid => $typename)
1113 {
1114 echo "<option value='${typeid}'";
1115 if ($typeid == $default_port_type)
1116 echo " selected";
1117 echo ">${typename}</option>\n";
1118 }
1119 echo "</select>";
1120 echo "<input type=submit value='Parse output'><br>\n";
1121 echo "<textarea name=input cols=100 rows=50></textarea><br>\n";
1122 echo '</form>';
1123 finishPortlet();
1124}
1125
1126function renderNetworkForObject ($object_id=0)
1127{
1128 global $root, $pageno, $tabno;
1129 if ($object_id <= 0)
1130 {
591ff2c4 1131 showError ('Invalid object_id', __FUNCTION__);
e673ee24
DO
1132 return;
1133 }
1134 showMessageOrError();
1135 startPortlet ('Network Addresses');
1136 $addresses = getObjectAddresses ($object_id);
1137 usort($addresses, 'sortAddresses');
1138 echo "<table cellspacing=0 cellpadding='5' align='center' class='widetable'>\n";
1139 echo "<tr><th>&nbsp;</th><th>Interface name</th><th>IP Address</th><th>Description</th><th>Type</th><th>Misc</th><th>&nbsp</th></tr>\n";
1140 foreach ($addresses as $addr)
1141 {
1142 if (strlen($addr['address_name'])>40)
1143 $address_name = substr($addr['address_name'],0,38).'...';
1144 else
1145 $address_name = $addr['address_name'];
1146
1147 $virtnum = countRefsOfType($addr['references'], 'virtual', 'eq');
1148 $sharednum = countRefsOfType($addr['references'], 'shared', 'eq');
1149 $regnum = countRefsOfType($addr['references'], 'regular', 'eq');
1150 $notvirtnum = countRefsOfType($addr['references'], 'virtual', 'neq');
1151
1152 if ($addr['address_reserved']=='yes')
24e85a1a 1153 $class='trerror';
e673ee24 1154 elseif ($addr['type']!='virtual' && $regnum>0)
24e85a1a 1155 $class='trerror';
e673ee24 1156 elseif ($addr['type']=='regular' && $sharednum>0)
24e85a1a 1157 $class='trerror';
e673ee24
DO
1158 else
1159 $class='';
1160
1161 echo "<form action='process.php'>";
1162 echo "<input type=hidden name=page value='${pageno}'>\n";
1163 echo "<input type=hidden name=tab value='${tabno}'>\n";
1164 echo "<input type=hidden name=op value=editAddressFromObject>";
1165 echo "<input type=hidden name=object_id value='$object_id'>";
1166 echo "<input type=hidden name=ip value='${addr['ip']}'>";
1167 echo "<tr class='$class'><td><a href='process.php?op=delAddrFObj&page=${pageno}&tab=${tabno}&ip=${addr['ip']}&object_id=$object_id'>";
1168 printImageHREF ('delete', 'Delete this IPv4 address');
1169 echo "</a></td>";
1170 echo "<td><input type='text' name='bond_name' value='${addr['name']}' size=10></td>";
1171 echo "<td><a href='${root}?page=ipaddress&ip=${addr['ip']}'>${addr['ip']}</a></td>";
1172 echo "<td class='description'>$address_name</td>\n";
1173 echo "<td><select name='bond_type'>";
1174 foreach (array('regular'=>'Regular', 'virtual'=>'Virtual', 'shared'=>'Shared') as $n => $v)
1175 {
1176 echo "<option value='$n'";
1177 if ($addr['type'] == $n)
1178 echo " selected";
1179 echo ">$v</option>";
1180 }
1181 echo "</td><td>";
1182 if ($addr['address_reserved']=='yes')
1183 echo "<b>Reserved</b>; ";
1184
1185 if ($addr['type'] == 'virtual')
1186 {
1187 if ($notvirtnum > 0)
1188 {
1189 echo " Owners: ";
1190 printRefsOfType($addr['references'], 'virtual', 'neq');
1191 }
1192 }
1193 elseif ($addr['type'] == 'shared')
1194 {
1195 if ($sharednum > 0)
1196 {
1197 echo " Peers: ";
1198 printRefsOfType($addr['references'], 'shared', 'eq');
1199 echo ";";
1200 }
1201 if ($virtnum > 0)
1202 {
1203 echo " Virtuals: ";
1204 printRefsOfType($addr['references'], 'virtual', 'eq');
1205 echo ";";
1206 }
1207 if ($regnum > 0)
1208 {
1209 echo " Collisions: ";
1210 printRefsOfType($addr['references'], 'regular', 'eq');
1211 }
1212
1213 }
1214 else
1215 {
1216 if ($virtnum > 0)
1217 {
1218 echo " Virtuals: ";
1219 printRefsOfType($addr['references'], 'virtual', 'eq');
1220 echo ";";
1221 }
1222 if ($notvirtnum > 0)
1223 {
1224 echo " Collisions: ";
1225 printRefsOfType($addr['references'], 'virtual', 'neq');
1226 }
1227 }
1228
1229 echo "</td><td><input type=submit value='OK'></td></form></tr>\n";
1230 }
1231
1232
1233 echo "<form action='${root}process.php'><tr><td colspan=2><input type='text' size='10' name='name' tabindex=100></td>\n";
1234 echo "<input type=hidden name=page value='${pageno}'>\n";
1235 echo "<input type=hidden name=tab value='${tabno}'>\n";
1236 echo "<input type=hidden name=op value=addAddrFObj>\n";
1237 echo "<input type=hidden name=object_id value='$object_id'>\n";
1238
1239 echo "<td><input type=text name='ip' tabindex=101>\n";
1240 echo "</td><td><select name='type' tabindex=102>";
1241 echo "<option value='regular'>Regular</option>";
1242 echo "<option value='virtual'>Virtual</option>";
1243 echo "<option value='shared'>Shared</option>";
1244 echo "</select>";
1245 echo "</td><td colspan=3><input type='submit' value='Add a new interface' tabindex=103></td></tr></form>";
1246 echo "</table><br>\n";
1247 finishPortlet();
1248
1249}
1250
1251function printLog ($log)
1252{
1253 foreach ($log as $record)
1254 echo "<div class=msg_${record['code']}>${record['message']}</div>";
1255}
1256
1257/*
1258The following conditions must be followed:
12591. We can mount onto free atoms only. This means: if any record for an atom
1260already exists in RackSpace, it can't be used for mounting.
12612. We can't unmount from 'W' atoms. Operator should review appropriate comments
1262and either delete them before unmounting or refuse to unmount the object.
1263*/
1264
1265// We extensively use $_REQUEST in the function.
1266function renderRackSpaceForObject ($object_id = 0)
1267{
1268 if ($object_id <= 0)
1269 {
591ff2c4 1270 showError ('Invalid object_id', __FUNCTION__);
e673ee24
DO
1271 return;
1272 }
1273 $is_submit = isset ($_REQUEST['got_atoms']);
1274 $is_update = isset ($_REQUEST['rackmulti'][0]);
1275 $info = getObjectInfo ($object_id);
1276 if ($info == NULL)
1277 {
591ff2c4 1278 showError ('getObjectInfo() failed', __FUNCTION__);
e673ee24
DO
1279 return;
1280 }
1281 // Always process occupied racks plus racks chosen by user. First get racks with
1282 // already allocated rackspace...
1283 $workingRacksData = getResidentRacksData ($object_id);
1284 if ($workingRacksData === NULL)
1285 {
1286 print_r ($workingRacksData);
591ff2c4 1287 showError ('getResidentRacksData() failed', __FUNCTION__);
e673ee24
DO
1288 return;
1289 }
1290
1291 // ...and then add those chosen by user (if any).
1292 if ($is_update)
1293 foreach ($_REQUEST['rackmulti'] as $cand_id)
1294 {
1295 if (!isset ($workingRacksData[$cand_id]))
1296 {
1297 $rackData = getRackData ($cand_id);
1298 if ($rackData == NULL)
1299 {
591ff2c4 1300 showError ('getRackData() failed', __FUNCTION__);
e673ee24
DO
1301 return NULL;
1302 }
1303 $workingRacksData[$cand_id] = $rackData;
1304 }
1305 }
1306
1307 // Do it only once...
1308 foreach ($workingRacksData as &$rackData)
1309 applyObjectMountMask ($rackData, $object_id);
1310 // Now we workaround an old caveat: http://bugs.php.net/bug.php?id=37410
1311 unset ($rackData);
1312
1313 // Here we process form submit by trying to save all submitted info to database.
1314 if ($is_submit)
1315 {
1316 $oldMolecule = getMoleculeForObject ($object_id);
1317 $worldchanged = FALSE;
1318 $log = array();
1319 foreach ($workingRacksData as $rack_id => $rackData)
1320 {
1321 $logrecord = processGridForm ($rackData, 'F', 'T', $object_id);
1322 $log[] = $logrecord;
1323 if ($logrecord['code'] != 300)
1324 {
1325 $worldchanged = TRUE;
1326 // Reload our working copy after form processing.
1327 $rackData = getRackData ($rack_id);
1328 if ($rackData == NULL)
4d2e93f2 1329 $log[] = array ('code' => 500, 'message' => 'Working copy update failed in ', __FUNCTION__);
e673ee24
DO
1330 applyObjectMountMask ($rackData, $object_id);
1331 $workingRacksData[$rack_id] = $rackData;
1332 }
1333 }
1334 if ($worldchanged)
1335 {
1336 // Log a record.
1337 $newMolecule = getMoleculeForObject ($object_id);
1338 $oc = count ($oldMolecule);
1339 $nc = count ($newMolecule);
1340 $omid = $oc ? createMolecule ($oldMolecule) : 'NULL';
1341 $nmid = $nc ? createMolecule ($newMolecule) : 'NULL';
1342 global $remote_username;
1343 $comment = empty ($_REQUEST['comment']) ? 'NULL' : "'${_REQUEST['comment']}'";
1344 $query =
1345 "insert into MountOperation(object_id, old_molecule_id, new_molecule_id, user_name, comment) " .
1346 "values (${object_id}, ${omid}, ${nmid}, '${remote_username}', ${comment})";
1347 global $dbxlink;
1348 $result = $dbxlink->query ($query);
1349 if ($result == NULL)
1350 $log[] = array ('code' => 'error', 'message' => 'SQL query failed during history logging.');
1351 else
1352 $log[] = array ('code' => 'success', 'message' => 'History logged.');
1353 }
1354 printLog ($log);
1355 }
1356
1357 // This is the time for rendering.
1358 global $root, $pageno, $tabno;
1359 echo "<form id='racks' action='${root}'>";
1360 echo "<input type=hidden name=page value='${pageno}'>\n";
1361 echo "<input type=hidden name=tab value='${tabno}'>\n";
1362 echo "<input type=hidden name=object_id value='${object_id}'>\n";
1363 // Main layout starts.
1364 echo "<table border=0 class=objectview cellspacing=0 cellpadding=0><tr>";
1365
1366 // Left portlet with rack list.
1367 echo "<td class=pcleft height='1%'>";
1368 startPortlet ('Racks');
1369 $allRacksData = getRacksForRow();
4b8d413e
DO
1370 if (count ($allRacksData) <= getConfigVar ('RACK_PRESELECT_THRESHOLD'))
1371 {
1372 foreach (array_keys ($allRacksData) as $rack_id)
1373 {
1374 $rackData = getRackData ($rack_id);
1375 if ($rackData == NULL)
1376 {
1377 showError ('getRackData() failed', __FUNCTION__);
1378 return NULL;
1379 }
1380 $workingRacksData[$rack_id] = $rackData;
1381 }
1382 foreach ($workingRacksData as &$rackData)
1383 applyObjectMountMask ($rackData, $object_id);
1384 unset ($rackData);
1385 }
1386 renderRackMultiSelect ('rackmulti[]', $allRacksData, array_keys ($workingRacksData));
e673ee24
DO
1387 echo "<br>";
1388 echo "<br>";
1389 finishPortlet();
1390 echo "</td>";
1391
1392 // Middle portlet with comment and submit.
1393 echo "<td class=pcleft>";
1394 startPortlet ('Comment');
1395 echo "<textarea name=comment rows=10 cols=40></textarea><br>\n";
1396 echo "<input type=submit value='Save' name=got_atoms>\n";
1397 echo "<br>";
1398 echo "<br>";
1399 finishPortlet();
1400 echo "</td>";
1401
1402 // Right portlet with rendered racks. If this form submit is not final, we have to
1403 // reflect the former state of the grid in current form.
1404 echo "<td class=pcright rowspan=2 height='1%'>";
1405 startPortlet ('Working copy');
1406 echo '<table border=0 cellspacing=10 align=center><tr>';
1407 foreach ($workingRacksData as $rack_id => $rackData)
1408 {
1409 // Order is important here: only original allocation is highlighted.
1410 highlightObject ($rackData, $object_id);
1411 markupAtomGrid ($rackData, 'T');
1412 // If we have a form processed, discard user input and show new database
1413 // contents.
1414 if (!$is_submit and $is_update)
1415 mergeGridFormToRack ($rackData);
1416 echo "<td valign=top>";
1417 echo "<center>\n<h2>${rackData['name']}</h2>\n";
1418 echo "<table class=rack border=0 cellspacing=0 cellpadding=1>\n";
1419 echo "<tr><th width='10%'>&nbsp;</th><th width='20%'>Front</th>";
1420 echo "<th width='50%'>Interior</th><th width='20%'>Back</th></tr>\n";
1421 renderAtomGrid ($rackData);
9b7468b7
DO
1422 echo "<tr><th width='10%'>&nbsp;</th><th width='20%'>Front</th>";
1423 echo "<th width='50%'>Interior</th><th width='20%'>Back</th></tr>\n";
e673ee24
DO
1424 echo "</table></center>\n";
1425 echo '</td>';
1426 }
1427 echo "</tr></table>";
1428 finishPortlet();
1429 echo "</td>\n";
1430
1431 echo "</form>\n";
1432 echo "</tr></table>\n";
1433}
1434
1435function renderMolecule ($mdata, $object_id)
1436{
1437 // sort data out
1438 $rackpack = array();
1439 global $loclist;
1440 foreach ($mdata as $dummy => $rua)
1441 {
1442 $rack_id = $rua['rack_id'];
1443 $unit_no = $rua['unit_no'];
1444 $atom = $rua['atom'];
1445 if (!isset ($rackpack[$rack_id]))
1446 {
1447 $rackData = getRackData ($rack_id);
1448 for ($i = $rackData['height']; $i > 0; $i--)
1449 for ($locidx = 0; $locidx < 3; $locidx++)
1450 $rackData[$i][$locidx]['state'] = 'F';
1451 $rackpack[$rack_id] = $rackData;
1452 }
1453 $rackpack[$rack_id][$unit_no][$loclist[$atom]]['state'] = 'T';
1454 $rackpack[$rack_id][$unit_no][$loclist[$atom]]['object_id'] = $object_id;
1455 }
1456 // now we have some racks to render
1457 foreach ($rackpack as $dummy => $rackData)
1458 {
1459 markAllSpans ($rackData);
1460 echo "<table class=molecule cellspacing=0>\n";
1461 echo "<caption>${rackData['name']}</caption>\n";
1462 echo "<tr><th width='10%'>&nbsp;</th><th width='20%'>Front</th><th width='50%'>Interior</th><th width='20%'>Back</th></tr>\n";
1463 for ($i = $rackData['height']; $i > 0; $i--)
1464 {
1465 echo "<tr><th>$i</th>";
1466 for ($locidx = 0; $locidx < 3; $locidx++)
1467 {
1468 $state = $rackData[$i][$locidx]['state'];
1469 echo "<td class=state_${state}>&nbsp;</td>\n";
1470 }
1471 echo "</tr>\n";
1472 }
1473 echo "</table>\n";
1474 }
1475}
1476
1477function renderUnmountedObjectsPortlet ()
1478{
1479 startPortlet ('Unmounted objects');
1480 $objs = getUnmountedObjects();
1481 if ($objs === NULL)
1482 {
591ff2c4 1483 showError ('getUnmountedObjects() failed', __FUNCTION__);
e673ee24
DO
1484 return;
1485 }
1486 global $root, $nextorder;
1487 $order = 'odd';
1488 echo '<br><br><table border=0 cellpadding=5 cellspacing=0 align=center class=cooltable>';
18d94c29 1489 echo '<tr><th>Common name</th><th>Visible label</th><th>Asset number</th><th>Barcode</th></tr>';
e673ee24
DO
1490 foreach ($objs as $obj)
1491 {
1492 echo "<tr class=row_${order}><td><a href='${root}?page=object&object_id=${obj['id']}'>${obj['dname']}</a></td>";
1493 echo "<td>${obj['label']}</td>";
18d94c29
DO
1494 echo "<td>${obj['asset_no']}</td>";
1495 echo "<td>${obj['barcode']}</td></tr>";
e673ee24
DO
1496 $order = $nextorder[$order];
1497 }
1498 echo "</table><br>\n";
1499 finishPortlet();
1500}
1501
1502function renderProblematicObjectsPortlet ()
1503{
1504 startPortlet ('Problematic objects');
1505 $objs = getProblematicObjects();
1506 if ($objs === NULL)
1507 {
591ff2c4 1508 showError ('getProblematicObjects() failed', __FUNCTION__);
e673ee24
DO
1509 return;
1510 }
1511 global $root, $nextorder;
1512 $order = 'odd';
1513 echo '<br><br><table border=0 cellpadding=5 cellspacing=0 align=center class=cooltable>';
1514 echo '<tr><th>Type</th><th>Common name</th></tr>';
1515 foreach ($objs as $obj)
1516 {
1517 echo "<tr class=row_${order}><td>${obj['objtype_name']}</td>";
1518 echo "<td><a href='${root}?page=object&object_id=${obj['id']}'>${obj['dname']}</a></tr>";
1519 $order = $nextorder[$order];
1520 }
1521 echo "</table><br>\n";
1522 finishPortlet();
1523}
1524
1525function renderObjectGroupSummary ()
1526{
1527 global $root;
20c901a7
DO
1528 $tagfilter = isset ($_REQUEST['tagfilter']) ? $_REQUEST['tagfilter'] : array();
1529 $tagfilter = complementByKids ($tagfilter);
e673ee24
DO
1530 $summary = getObjectGroupInfo();
1531 if ($summary === NULL)
1532 {
591ff2c4 1533 showError ('getObjectGroupInfo() failed', __FUNCTION__);
e673ee24
DO
1534 return;
1535 }
1536 echo "<table border=0 class=objectview>\n";
1537 echo "<tr><td class=pcleft width='25%'>";
1538
1539 startPortlet ('Summary');
1540 foreach ($summary as $gi)
e673ee24 1541 echo "<a href='${root}?page=objgroup&group_id=${gi['id']}'><b>${gi['name']}</b></a> <i>(${gi['count']})</i><br>";
e673ee24
DO
1542 finishPortlet();
1543
1544 echo '</td><td class=pcright>';
1545 renderUnmountedObjectsPortlet();
1546 echo '</td><td class=pcright>';
1547 renderProblematicObjectsPortlet();
20c901a7 1548 echo '</td><td class=pcright>';
7cc02fc1
DO
1549 startPortlet ('Tag filter');
1550 renderTagFilterSelect ($tagfilter, 'object');
1551 finishPortlet();
1552 echo "</td></tr></table>\n";
1553}
1554
1555function renderObjectSpace ()
1556{
105cea6e 1557 global $root, $taglist, $tagtree;
7cc02fc1
DO
1558 echo "<table border=0 class=objectview>\n";
1559 echo "<tr><td class=pcleft width='50%'>";
1560 startPortlet ('View all by type');
1561 $groupInfo = getObjectGroupInfo();
1562 if ($groupInfo === NULL)
1563 {
1564 showError ('getObjectGroupInfo() failed', __FUNCTION__);
1565 return;
1566 }
1567 if (count ($groupInfo) == 0)
1568 echo "No objects exist in DB";
1569 else
1570 {
1571 echo '<div align=left><ul>';
1572 foreach ($groupInfo as $gi)
1573 echo "<li><a href='${root}?page=objgroup&group_id=${gi['id']}'>${gi['name']}</a> (${gi['count']})</li>";
1574 echo '</ul></div>';
1575 }
1576 finishPortlet();
1577
1578 echo '</td><td class=pcright>';
1579
1580 startPortlet ('View all by tag');
1581 if (count ($taglist) == 0)
1582 echo "No tags exist in DB";
1583 else
1584 renderTagCloud ('object');
1585 finishPortlet();
e673ee24
DO
1586 echo "</td></tr></table>\n";
1587}
1588
466dcbe6 1589function renderObjectGroup ()
7cc02fc1
DO
1590{
1591 global $root, $pageno, $tabno, $nextorder, $taglist, $tagtree;
2c6c7645 1592 assertUIntArg ('group_id', __FUNCTION__, TRUE);
7cc02fc1
DO
1593 $group_id = $_REQUEST['group_id'];
1594 $tagfilter = isset ($_REQUEST['tagfilter']) ? $_REQUEST['tagfilter'] : array();
1595 $tagfilter_str = getStringFromTrail (getExplicitTagsOnly (buildTrailFromIds ($tagfilter)));
1596 $tagfilter = complementByKids ($tagfilter);
1597 echo "<form>\n";
1598 echo "<input type=hidden name=page value=${pageno}>\n";
1599 echo "<input type=hidden name=group_id value=${group_id}>\n";
1600 echo "<table border=0 class=objectview>\n";
1601 echo "<tr><td class=pcleft width='25%'>";
1602 startPortlet ('change type');
1603 $groupInfo = getObjectGroupInfo();
1604 if ($groupInfo === NULL)
1605 {
1606 showError ('getObjectGroupInfo() failed', __FUNCTION__);
1607 return;
1608 }
1609 if (count ($groupInfo) == 0)
1610 echo "No objects exist in DB";
1611 else
1612 {
1613 echo '<div align=left><ul>';
1614 foreach ($groupInfo as $gi)
1615 {
1616 echo "<li><a href='${root}?page=${pageno}&group_id=${gi['id']}&tagfilter[]=${tagfilter_str}'>";
105cea6e
DO
1617 if ($gi['id'] == $group_id)
1618 echo '<strong>';
1619 echo "${gi['name']}</a>";
1620 if ($gi['id'] == $group_id)
1621 echo '</strong>';
1622 echo " (${gi['count']})";
1623 if ($gi['id'] == $group_id)
1624 echo ' &larr;';
1625 echo "</li>";
7cc02fc1
DO
1626 }
1627 echo '</ul></div>';
1628 }
1629 finishPortlet();
1630
1631 echo '</td><td class=pcleft>';
1632
1633 startPortlet ('Objects');
1634 $objects = getObjectList ($group_id, $tagfilter);
1635 if ($objects === NULL)
1636 {
1637 showError ('getObjectList() failed', __FUNCTION__);
1638 return;
1639 }
1640 echo '<br><br><table border=0 cellpadding=5 cellspacing=0 align=center class=cooltable>';
1641 echo '<tr><th>Common name</th><th>Visible label</th><th>Asset tag</th><th>Barcode</th><th>Rack</th></tr>';
1642 $order = 'odd';
1643 foreach ($objects as $obj)
1644 {
1645 echo "<tr class=row_${order}><td><a href='${root}?page=object&object_id=${obj['id']}'>${obj['dname']}</a></td>";
1646 echo "<td>${obj['label']}</td>";
1647 echo "<td>${obj['asset_no']}</td>";
1648 echo "<td>${obj['barcode']}</td>";
1649 if ($obj['rack_id'])
1650 echo "<td><a href='${root}?page=rack&rack_id=${obj['rack_id']}'>${obj['Rack_name']}</a></td>";
1651 else
1652 echo '<td>Unmounted</td>';
1653 echo '</tr>';
1654 $order = $nextorder[$order];
1655 }
1656 echo '</table>';
1657 finishPortlet();
1658
1659 echo "</td><td class=pcright width='25%'>";
1660
1661 startPortlet ('change filter');
1662 renderTagFilterSelect ($tagfilter, 'object');
1663 echo "<input type=submit value='Apply'>\n";
1664 finishPortlet();
1665 echo "</td></tr></table>\n";
1666 echo '</form>';
1667}
1668
1669function renderObjectGroup_old ()
e673ee24
DO
1670{
1671 global $root;
2c6c7645 1672 assertUIntArg ('group_id', __FUNCTION__);
466dcbe6 1673 $group_id = $_REQUEST['group_id'];
e673ee24
DO
1674 $summary = getObjectGroupInfo();
1675 if ($summary == NULL)
1676 {
591ff2c4 1677 showError ('getObjectGroupInfo() failed', __FUNCTION__);
e673ee24
DO
1678 return;
1679 }
1680 $objects = getObjectList ($group_id);
1681 if ($objects === NULL)
1682 {
591ff2c4 1683 showError ('getObjectList() failed', __FUNCTION__);
e673ee24
DO
1684 return;
1685 }
1686 echo "<table border=0 class=objectview>\n";
1687 echo "<tr><td class=pcleft width='25%'>";
1688
1689 startPortlet ('All objects');
1690 foreach ($summary as $gi)
1691 {
1692 echo "<a href='${root}?page=objgroup&group_id=${gi['id']}'><b>${gi['name']}</b></a> <i>(${gi['count']})</i><br>";
1693 }
1694 finishPortlet();
1695
1696 echo '</td><td class=pcright>';
1697
1698 startPortlet ('Object group');
1699 echo '<br><br><table border=0 cellpadding=5 cellspacing=0 align=center class=cooltable>';
18d94c29 1700 echo '<tr><th>Common name</th><th>Visible label</th><th>Asset tag</th><th>Barcode</th><th>Rack</th></tr>';
e673ee24
DO
1701 $order = 'odd';
1702 global $nextorder;
1703 foreach ($objects as $obj)
1704 {
1705 echo "<tr class=row_${order}><td><a href='${root}?page=object&object_id=${obj['id']}'>${obj['dname']}</a></td>";
1706 echo "<td>${obj['label']}</td>";
1707 echo "<td>${obj['asset_no']}</td>";
18d94c29 1708 echo "<td>${obj['barcode']}</td>";
e673ee24
DO
1709 if ($obj['rack_id'])
1710 echo "<td><a href='${root}?page=rack&rack_id=${obj['rack_id']}'>${obj['Rack_name']}</a></td>";
1711 else
1712 echo '<td>Unmounted</td>';
1713 echo '</tr>';
1714 $order = $nextorder[$order];
1715 }
1716 echo '</table>';
1717 finishPortlet();
1718
1719 echo "</td></tr></table>";
1720}
1721
1722function renderEmptyPortsSelect ($port_id, $type_id)
1723{
1724 $ports = getEmptyPortsOfType($type_id);
1725 usort($ports, 'sortEmptyPorts');
1726 foreach ($ports as $port)
1727 {
1728 if ($port_id == $port['Port_id'])
1729 continue;
1730 echo "<option value='${port['Port_id']}' onclick='getElementById(\"remote_port_name\").value=\"${port['Port_name']}\"; getElementById(\"remote_object_name\").value=\"${port['Object_name']}\";'>${port['Object_name']} ${port['Port_name']}</option>\n";
1731 }
1732}
1733
1734function renderObjectAddressesAndNames ()
1735{
1736 $addresses = getObjectAddressesAndNames();
1737 usort($addresses, 'sortObjectAddressesAndNames');
1738 foreach ($addresses as $address)
1739 {
1740 echo "<option value='${address['ip']}' onclick='getElementById(\"ip\").value=\"${address['ip']}\";'>${address['object_name']} ${address['name']} ${address['ip']}</option>\n";
1741 }
1742}
1743
1744// History viewer for history-enabled simple dictionaries.
1745function renderHistory ($object_type, $object_id)
1746{
1747 switch ($object_type)
1748 {
1749 case 'row':
1750 $query = "select ctime, user_name, name, deleted, comment from RackRowHistory where id = ${object_id} order by ctime";
1751 $header = '<tr><th>change time</th><th>author</th><th>rack row name</th><th>is deleted?</th><th>rack row comment</th></tr>';
1752 $extra = 4;
1753 break;
1754 case 'rack':
1755 $query =
1756 "select ctime, user_name, rh.name, rh.deleted, d.dict_value as name, rh.height, rh.comment " .
1757 "from RackHistory as rh left join Dictionary as d on rh.row_id = d.dict_key " .
1758 "natural join Chapter " .
1759 "where chapter_name = 'RackRow' and rh.id = ${object_id} order by ctime";
1760 $header = '<tr><th>change time</th><th>author</th><th>rack name</th><th>is deleted?</th><th>rack row name</th><th>rack height</th><th>rack comment</th></tr>';
1761 $extra = 6;
1762 break;
1763 case 'object':
1764 $query =
1765 "select ctime, user_name, name, label, barcode, asset_no, deleted, has_problems, dict_value, comment " .
1766 "from RackObjectHistory inner join Dictionary on objtype_id = dict_key natural join Chapter " .
1767 "where chapter_name = 'RackObjectType' and id=${object_id} order by ctime";
1768 $header = '<tr><th>change time</th><th>author</th><th>common name</th><th>visible label</th><th>barcode</th><th>asset no</th><th>is deleted?</th><th>has problems?</th><th>object type</th><th>comment</th></tr>';
1769 $extra = 9;
1770 break;
1771 default:
591ff2c4 1772 showError ("Uknown object type '${object_type}'", __FUNCTION__);
e673ee24
DO
1773 return;
1774 }
1775 global $dbxlink;
1776 $result = $dbxlink->query ($query);
1777 if ($result == NULL)
1778 {
591ff2c4 1779 showError ('SQL query failed', __FUNCTION__);
e673ee24
DO
1780 return;
1781 }
1782 echo '<table border=0 cellpadding=5 cellspacing=0 align=center class=cooltable>';
1783 $order = 'odd';
1784 global $nextorder;
1785 echo $header;
1786 while ($row = $result->fetch (PDO::FETCH_NUM))
1787 {
1788 echo "<tr class=row_${order}><td>${row[0]}</td>";
1789 for ($i = 1; $i <= $extra; $i++)
1790 echo "<td>" . $row[$i] . "</td>";
1791 echo "</tr>\n";
1792 $order = $nextorder[$order];
1793 }
1794 echo "</table><br>\n";
1795}
1796
1797function renderRackspaceHistory ()
1798{
1799 global $root, $nextorder, $pageno, $tabno;
1800 $order = 'odd';
1801 $history = getRackspaceHistory();
1802 // Show the last operation by default.
1803 if (isset ($_REQUEST['op_id']))
1804 $op_id = $_REQUEST['op_id'];
1805 elseif (isset ($history[0]['mo_id']))
1806 $op_id = $history[0]['mo_id'];
1807 else $op_id = NULL;
1808
1809 $omid = NULL;
1810 $nmid = NULL;
1811 $object_id = 1;
1812 if ($op_id)
1813 list ($omid, $nmid) = getOperationMolecules ($op_id);
1814
1815 // Main layout starts.
1816 echo "<table border=0 class=objectview cellspacing=0 cellpadding=0>";
1817
1818 // Left top portlet with old allocation.
1819 echo "<tr><td class=pcleft>";
1820 startPortlet ('Old allocation');
1821 if ($omid)
1822 {
1823 $oldMolecule = getMolecule ($omid);
1824 renderMolecule ($oldMolecule, $object_id);
1825 }
1826 else
1827 echo "nothing";
1828 finishPortlet();
1829
1830 echo '</td><td class=pcright>';
1831
1832 // Right top portlet with new allocation
1833 startPortlet ('New allocation');
1834 if ($nmid)
1835 {
1836 $newMolecule = getMolecule ($nmid);
1837 renderMolecule ($newMolecule, $object_id);
1838 }
1839 else
1840 echo "nothing";
1841 finishPortlet();
1842
1843 echo '</td></tr><tr><td colspan=2>';
1844
1845 // Bottom portlet with list
1846
1847 startPortlet ('Rackspace allocation history');
1848 echo "<table border=0 cellpadding=5 cellspacing=0 align=center class=cooltable>\n";
1849 echo "<tr><th>timestamp</th><th>author</th><th>rack object ID</th><th>rack object type</th><th>rack object name</th><th>comment</th></tr>\n";
1850 foreach ($history as $row)
1851 {
1852 if ($row['mo_id'] == $op_id)
1853 $class = 'hl';
1854 else
1855 $class = "row_${order}";
1856 echo "<tr class=${class}><td><a href='${root}?page=${pageno}&tab=${tabno}&op_id=${row['mo_id']}'>${row['ctime']}</a></td>";
1857 echo "<td>${row['user_name']}</td>";
1858 echo "<td>${row['ro_id']}</td><td>${row['objtype_name']}</td><td>${row['name']}</td><td>${row['comment']}</td>\n";
1859 echo "</tr>\n";
1860 $order = $nextorder[$order];
1861 }
1862 echo "</table>\n";
1863 finishPortlet();
1864
1865 echo '</td></tr></table>';
1866
1867}
1868
1869function renderAddressspace ()
1870{
b3c50e6c 1871 global $root, $page;
a7fe7729 1872
74ccacff
DO
1873 echo "<table border=0 class=objectview>\n";
1874 echo "<tr><td class=pcleft>";
1875
a7fe7729 1876 startPortlet ('Subnets');
e673ee24 1877 echo "<table class='widetable' border=0 cellpadding=10 cellspacing=0 align='center'>\n";
74ccacff
DO
1878 $tagfilter = isset ($_REQUEST['tagfilter']) ? $_REQUEST['tagfilter'] : array();
1879 $tagfilter = complementByKids ($tagfilter);
1880 $addrspaceList = getAddressspaceList ($tagfilter);
119f2ad2 1881 echo "<tr><th>Subnet</th><th>Name</th><th>Utilization</th></tr>";
e673ee24
DO
1882 foreach ($addrspaceList as $iprange)
1883 {
119f2ad2
DO
1884 $range = getIPRange ($iprange['id']);
1885 $total = ($iprange['ip_bin'] | $iprange['mask_bin_inv']) - ($iprange['ip_bin'] & $iprange['mask_bin']) + 1;
1886 $used = count ($range['addrlist']);
1887 echo "<tr><td class=tdleft><a href='${root}?page=iprange&id=${iprange['id']}'>${iprange['ip']}/${iprange['mask']}</a></td>";
1888 echo "<td class=tdleft>${iprange['name']}</td><td class=tdleft>";
1889 renderProgressBar ($used/$total);
1890 echo " ${used}/${total}</td></tr>";
e673ee24
DO
1891 }
1892 echo "</table>\n";
a7fe7729 1893 finishPortlet();
74ccacff 1894 echo '</td><td class=pcright>';
5b7bd02e 1895 renderTagFilterPortlet ($tagfilter, 'ipv4net');
74ccacff 1896 echo "</td></tr></table>\n";
f973f491 1897}
a7fe7729 1898
f973f491
DO
1899function renderIPv4SLB ()
1900{
80e85ea1 1901 global $root, $page, $nextorder;
a7fe7729 1902
6fec9f39 1903 startPortlet ('SLB configuration');
b3c50e6c
DO
1904 echo "<table border=0 width='100%'><tr>";
1905 foreach (array ('vservices', 'rspools', 'rservers', 'lbs') as $pno)
e57dca7f 1906 echo "<td><h3><a href='${root}?page=${pno}'>" . $page[$pno]['title'] . "</a></h3></td>";
b3c50e6c
DO
1907 echo '</tr></table>';
1908 finishPortlet();
1909
c3bdc503 1910 $summary = getSLBSummary();
6fec9f39 1911 startPortlet ('SLB tactical overview');
4cadac8f
DO
1912 // A single id-keyed array isn't used here to preserve existing
1913 // order of LBs returned by getSLBSummary()
c3bdc503
DO
1914 $lblist = array();
1915 $lbdname = array();
4cadac8f 1916 foreach ($summary as $vipdata)
da04825a 1917 foreach (array_keys ($vipdata['lblist']) as $lb_object_id)
c3bdc503
DO
1918 if (!in_array ($lb_object_id, $lblist))
1919 {
1920 $oi = getObjectInfo ($lb_object_id);
1921 $lbdname[$lb_object_id] = $oi['dname'];
1922 $lblist[] = $lb_object_id;
1923 }
1924 if (!count ($summary))
1925 echo 'none configured';
1926 else
1927 {
80e85ea1 1928 $order = 'odd';
c3bdc503 1929 echo "<table class='widetable' border=0 cellpadding=5 cellspacing=0 align='center'>\n";
a7bc13c8 1930 echo "<tr><th>VS&nbsp;&darr; LB&nbsp;&rarr;</th>";
c3bdc503 1931 foreach ($lblist as $lb_object_id)
71b8bda1 1932 echo "<th><a href='${root}?page=object&tab=default&object_id=${lb_object_id}'>" . $lbdname[$lb_object_id] . "</a></th>";
c3bdc503 1933 echo "</tr>\n";
4cadac8f
DO
1934 foreach ($summary as $vsid => $vsdata)
1935 {
80e85ea1 1936 echo "<tr class=row_${order}><td class=tdleft><a href='$root?page=vservice&tab=default&id=${vsid}'>";
8d790216 1937 echo buildVServiceName ($vsdata);
6fec9f39
DO
1938 echo '</a>';
1939 if (!empty ($vsdata['name']))
1940 echo " (${vsdata['name']})";
1941 echo "</td>";
4cadac8f 1942 foreach ($lblist as $lb_object_id)
da04825a 1943 {
60fbcece 1944 echo '<td class=tdleft>';
2b4eee17 1945 if (!isset ($vsdata['lblist'][$lb_object_id]))
da04825a
DO
1946 echo '&nbsp;';
1947 else
6fec9f39
DO
1948 {
1949 echo $vsdata['lblist'][$lb_object_id]['size'];
c0ae6968 1950 echo " (<a href='${root}?page=rspool&pool_id=";
6fec9f39
DO
1951 echo $vsdata['lblist'][$lb_object_id]['id'] . "'>";
1952 echo $vsdata['lblist'][$lb_object_id]['name'] . '</a>)';
1953 }
da04825a
DO
1954 echo '</td>';
1955 }
1956 echo "</tr>\n";
80e85ea1 1957 $order = $nextorder[$order];
4cadac8f 1958 }
c3bdc503
DO
1959 echo "</table>\n";
1960 }
a7fe7729 1961 finishPortlet ();
e673ee24
DO
1962}
1963
1964function renderAddNewRange ()
1965{
1966 global $root, $pageno, $tabno;
1967 showMessageOrError();
2a201216 1968
5c0bb421 1969 startPortlet ("Add New");
2a201216 1970 echo "<table class='widetable' border=0 cellpadding=10 align='center'>\n";
5c0bb421 1971 echo "<tr><th>Address range</th><th>Name</th><th>connected network</th><th>assign tags</th><th>&nbsp;</th></tr>\n";
2a201216
DY
1972 echo "<form name='add_new_range' action='process.php'>\n";
1973 echo "<input type=hidden name=op value=addRange>\n";
1974 echo "<input type=hidden name=page value='${pageno}'>\n";
1975 echo "<input type=hidden name=tab value='${tabno}'>\n";
5c0bb421 1976 echo "<tr valign=top><td class='tdcenter'><input type=text name='range' size=18 class='live-validate' tabindex=1></td>\n";
7059c1d2
DO
1977 echo "<td class='tdcenter'><input type=text name='name' size='20' tabindex=2></td>\n";
1978 echo "<td class='tdcenter'><input type=checkbox name='is_bcast' tabindex=3 checked></td>\n";
5c0bb421
DO
1979 echo "<td>\n";
1980 renderTagSelect();
1981 echo "</td>\n";
1982 echo "<td class='tdcenter'><input type=submit value='Add a new range' tabindex=4></td>\n";
1983 echo "</td></tr>\n";
2a201216 1984 echo "</form></table><br><br>\n";
5c0bb421 1985 finishPortlet();
2a201216 1986
5c0bb421 1987 startPortlet ("Manage Existing");
2a201216 1988 echo "<table class='widetable' border=0 cellpadding=10 align='center'>\n";
e673ee24 1989 $addrspaceList = getAddressspaceList();
283824c8 1990 echo "<tr><th>&nbsp;</th><th>Address range</th><th>Name</th><th>Utilization</th></tr>";
e673ee24
DO
1991 foreach ($addrspaceList as $iprange)
1992 {
1993 $range = getIPRange($iprange['id']);
dc462202 1994 $usedips = count ($range['addrlist']);
283824c8 1995 $totalips = ($iprange['ip_bin'] | $iprange['mask_bin_inv']) - ($iprange['ip_bin'] & $iprange['mask_bin']) + 1;
0c4605ab 1996 echo "<tr><td>";
e673ee24
DO
1997 if ($usedips == 0)
1998 {
0c4605ab 1999 echo "<a href='process.php?op=delRange&page=${pageno}&tab=${tabno}&id=${iprange['id']}'>";
e673ee24 2000 printImageHREF ('delete', 'Delete this IP range');
0c4605ab 2001 echo "</a>";
e673ee24
DO
2002 }
2003 else
0c4605ab 2004 printImageHREF ('nodelete', 'There are IP addresses allocated or reserved');
20c901a7
DO
2005 echo "</td>\n<td class=tdleft><a href='${root}?page=iprange&id=${iprange['id']}'>";
2006 echo "${iprange['ip']}/${iprange['mask']}</a></td><td class=tdleft>${iprange['name']}";
2007 echo "</td><td class=tdleft>";
283824c8
DO
2008 renderProgressBar ($usedips / $totalips);
2009 echo " ${usedips}/${totalips}";
e673ee24
DO
2010 echo "</td></tr>";
2011 }
cee27f1d 2012 echo "</table>";
5c0bb421 2013 finishPortlet();
e673ee24
DO
2014}
2015
2fe5476a 2016function renderIPRange ($id)
e673ee24 2017{
41bd8c87 2018 global $root, $pageno, $tabno;
545478d0
DO
2019 $netmaskbylen = array
2020 (
2021 32 => '255.255.255.255',
2022 31 => '255.255.255.254',
2023 30 => '255.255.255.252',
2024 29 => '255.255.255.248',
2025 28 => '255.255.255.240',
2026 27 => '255.255.255.224',
2027 26 => '255.255.255.192',
2028 25 => '255.255.255.128',
2029 24 => '255.255.255.0',
2030 23 => '255.255.254.0',
2031 22 => '255.255.252.0',
2032 21 => '255.255.248.0',
2033 20 => '255.255.240.0',
2034 19 => '255.255.224.0',
2035 18 => '255.255.192.0',
2036 17 => '255.255.128.0',
2037 16 => '255.255.0.0',
2038 15 => '255.254.0.0',
2039 14 => '255.252.0.0',
2040 13 => '255.248.0.0',
2041 12 => '255.240.0.0',
2042 11 => '255.224.0.0',
2043 10 => '255.192.0.0',
2044 9 => '255.128.0.0',
2045 8 => '255.0.0.0',
2046 7 => '254.0.0.0',
2047 6 => '252.0.0.0',
2048 5 => '248.0.0.0',
2049 4 => '240.0.0.0',
2050 3 => '224.0.0.0',
2051 2 => '192.0.0.0',
2052 1 => '128.0.0.0'
2053 );
2054 $wildcardbylen = array
2055 (
2056 32 => '0.0.0.0',
2057 31 => '0.0.0.1',
2058 30 => '0.0.0.3',
2059 29 => '0.0.0.7',
2060 28 => '0.0.0.15',
2061 27 => '0.0.0.31',
2062 26 => '0.0.0.63',
2063 25 => '0.0.0.127',
2064 24 => '0.0.0.255',
2065 23 => '0.0.1.255',
2066 22 => '0.0.3.255',
2067 21 => '0.0.7.255',
2068 20 => '0.0.15.255',
2069 19 => '0.0.31.255',
2070 18 => '0.0.63.255',
2071 17 => '0.0.127.255',
2072 16 => '0.0.255.25',
2073 15 => '0.1.255.255',
2074 14 => '0.3.255.255',
2075 13 => '0.7.255.255',
2076 12 => '0.15.255.255',
2077 11 => '0.31.255.255',
2078 10 => '0.63.255.255',
2079 9 => '0.127.255.255',
2080 8 => '0.255.255.255',
2081 7 => '1.255.255.255',
2082 6 => '3.255.255.255',
2083 5 => '7.255.255.255',
2084 4 => '15.255.255.255',
2085 3 => '31.255.255.255',
2086 2 => '63.255.255.255',
2087 1 => '127.255.255.255'
2088 );
b901bf1f 2089 $maxperpage = getConfigVar ('IPV4_ADDRS_PER_PAGE');
e673ee24
DO
2090 if (isset($_REQUEST['pg']))
2091 $page = $_REQUEST['pg'];
2092 else
2093 $page=0;
2094
e673ee24 2095 $range = getIPRange($id);
2034d968
DO
2096 echo "<table border=0 class=objectview cellspacing=0 cellpadding=0>";
2097 echo "<tr><td colspan=2 align=center><h1>${range['ip']}/${range['mask']}</h1><h2>${range['name']}</h2></td></tr>\n";
2098
2099 echo "<tr><td class=pcleft width='50%'>";
2100 startPortlet ('summary');
2101 $total = ($range['ip_bin'] | $range['mask_bin_inv']) - ($range['ip_bin'] & $range['mask_bin']) + 1;
2102 $used = count ($range['addrlist']);
2103 echo "<table border=0 cellspacing=0 cellpadding=3 width='100%'>\n";
2104 echo "<tr><th width='50%' class=tdright>Utilization:</th><td class=tdleft>";
2105 renderProgressBar ($used/$total);
2106 echo "&nbsp;${used}/${total}</td></tr>\n";
545478d0
DO
2107 echo "<tr><th width='50%' class=tdright>Netmask:</th><td class=tdleft>";
2108 echo $netmaskbylen[$range['mask']];
2109 echo "</td></tr>\n";
2110 echo "<tr><th width='50%' class=tdright>Wildcard bits:</th><td class=tdleft>";
2111 echo $wildcardbylen[$range['mask']];
2112 echo "</td></tr>\n";
41bd8c87 2113 printTagTRs();
2034d968
DO
2114 echo "</table><br>\n";
2115 finishPortlet();
2116 echo "</td>\n";
e673ee24 2117
2034d968
DO
2118 echo "<td class=pcright>";
2119 startPortlet ('details');
e673ee24
DO
2120 $startip = $range['ip_bin'] & $range['mask_bin'];
2121 $endip = $range['ip_bin'] | $range['mask_bin_inv'];
2122 $realstartip = $startip;
2123 $realendip = $endip;
2124 $numpages = 0;
2125 if($endip - $startip > $maxperpage)
2126 {
e673ee24
DO
2127 $numpages = ($endip - $startip)/$maxperpage;
2128 $startip = $startip + $page * $maxperpage;
2129 $endip = $startip + $maxperpage-1;
2130 }
2131 echo "<center>";
b901bf1f
DO
2132 if ($numpages)
2133 echo '<h3>' . long2ip ($startip) . ' ~ ' . long2ip ($endip) . '</h3>';
e673ee24
DO
2134 for ($i=0; $i<$numpages; $i++)
2135 {
2136 if ($i == $page)
2137 echo "<b>$i</b> ";
2138 else
a60e0851 2139 echo "<a href='${root}?page=${pageno}&tab=${tabno}&id=$id&pg=$i'>$i</a> ";
e673ee24
DO
2140 }
2141 echo "</center>";
2142
2143 echo "<table class='widetable' border=0 cellspacing=0 cellpadding=5 align='center'>\n";
2144 echo "<tr><th>Address</th><th>Name</th><th>Allocation</th></tr>\n";
2145
2146
2147 for($ip = $startip; $ip<=$endip; $ip++)
2148 {
dcee8072 2149 if (isset ($range['addrlist'][$ip]))
e673ee24
DO
2150 {
2151 $numshared = countRefsOfType($range['addrlist'][$ip]['references'], 'shared', 'eq');
2152 $numreg = countRefsOfType($range['addrlist'][$ip]['references'], 'regular', 'eq');
2153 $numvirt = countRefsOfType($range['addrlist'][$ip]['references'], 'virtual', 'eq');
602663f4
DO
2154 $numlb = count ($range['addrlist'][$ip]['lbrefs']);
2155 $numrs = count ($range['addrlist'][$ip]['rsrefs']);
e673ee24
DO
2156
2157 $addr = $range['addrlist'][$ip];
2158 if ( ($numshared > 0 && $numreg > 0) || $numreg > 1 )
24e85a1a 2159 echo "<tr class='trerror'>";
e485e609 2160 elseif ( $addr['reserved'] == 'yes' and $numshared+$numreg+$numvirt+$numlb+$numrs > 0)
24e85a1a 2161 echo "<tr class='trerror'>";
e673ee24
DO
2162 elseif ( $addr['reserved'] == 'yes')
2163 echo "<tr class='trbusy'>";
602663f4 2164 elseif ( $numshared > 0 || $numreg > 0 || $numlb > 0 || $numrs > 0)
e673ee24
DO
2165 echo "<tr class='trbusy'>";
2166 else
2167 echo "<tr>";
2168
2169 echo "<td><a href='${root}?page=ipaddress&ip=${addr['ip']}'>${addr['ip']}</a></td><td>${addr['name']}</td><td>";
6131056c 2170 $delim = '';
602663f4 2171 $prologue = '';
e673ee24 2172 if ( $addr['reserved'] == 'yes')
6131056c 2173 {
55434dd5 2174 echo "<b>Reserved</b> ";
6131056c
DO
2175 $delim = '; ';
2176 }
e673ee24
DO
2177 foreach ($range['addrlist'][$ip]['references'] as $ref)
2178 {
e26b085f 2179 echo "${delim}<a href='${root}?page=object&object_id=${ref['object_id']}'>";
db88e2de 2180 echo $ref['name'] . (empty ($ref['name']) ? '' : '@');
e26b085f
DO
2181 echo "${ref['object_name']}</a>";
2182 $delim = '; ';
e673ee24 2183 }
602663f4
DO
2184 if ($delim != '')
2185 {
2186 $delim = '';
2187 $prologue = '<br>';
2188 }
2189 foreach ($range['addrlist'][$ip]['lbrefs'] as $ref)
2190 {
2191 echo $prologue;
2192 $prologue = '';
2193 echo "${delim}<a href='${root}?page=object&object_id=${ref['object_id']}'>";
2194 echo "${ref['object_name']}</a>:<a href='${root}?page=vservice&id=${ref['vs_id']}'>";
2195 echo "${ref['vport']}/${ref['proto']}</a>&rarr;";
2196 $delim = '; ';
2197 }
2198 if ($delim != '')
2199 {
2200 $delim = '';
2201 $prologue = '<br>';
2202 }
2203 foreach ($range['addrlist'][$ip]['rsrefs'] as $ref)
2204 {
2205 echo $prologue;
2206 $prologue = '';
c0ae6968 2207 echo "${delim}&rarr;${ref['rsport']}@<a href='${root}?page=rspool&pool_id=${ref['rspool_id']}'>";
602663f4
DO
2208 echo "${ref['rspool_name']}</a>";
2209 $delim = '; ';
2210 }
e673ee24
DO
2211 echo "</td></tr>\n";
2212 }
2213 else
2214 {
2215 echo "<tr><td><a href='${root}?page=ipaddress&ip=".long2ip($ip)."'>".long2ip($ip)."</a></td><td>&nbsp;</td><td>&nbsp;</td></tr>\n";
2216 }
2217 }
2218
2219 echo "</table>";
2034d968
DO
2220 finishPortlet();
2221 echo "</td></tr></table>\n";
e673ee24
DO
2222}
2223
2fe5476a 2224function renderIPRangeProperties ($id)
e673ee24
DO
2225{
2226 global $pageno, $tabno;
e673ee24
DO
2227 showMessageOrError();
2228 $range = getIPRange($id);
2229 echo "<center><h1>${range['ip']}/${range['mask']}</h1></center>\n";
2230 echo "<table border=0 cellpadding=10 cellpadding=1 align='center'>\n";
2231 echo "<form action='process.php'><input type=hidden name=op value=editRange>";
2232 echo "<input type=hidden name=page value='${pageno}'>\n";
2233 echo "<input type=hidden name=tab value='${tabno}'>\n";
2234 echo "<input type=hidden name=id value='${id}'>";
2235 echo "<tr><td class='tdright'>Name:</td><td class='tdleft'><input type=text name=name size=20 value='${range['name']}'></tr><tr><td colspan=2 class='tdcenter'><input type=submit value='Update range'></td></form></tr>";
2236 echo "</table>\n";
2237
2238}
2239
2240function renderIPAddress ()
2241{
2242 global $root;
2243 $ip = $_REQUEST['ip'];
2244 $address = getIPAddress($ip);
2245 echo "<center><h1>$ip</h1>";
2246 if ($address['exists'] == 1)
2247 echo "<h2>${address['name']}</h2>";
2248 echo "</center>\n";
2249
2250// echo "<table width='100%' cesspadding=5 cellspacing=0 border=0 align='center'>";
2251// echo "<tr valign='top'><td>";
2252
e673ee24
DO
2253 $numshared = countRefsOfType($address['bonds'], 'shared', 'eq');
2254 $numreg = countRefsOfType($address['bonds'], 'regular', 'eq');
2255 $numvirt = countRefsOfType($address['bonds'], 'virtual', 'eq');
2256
59bebe2b
DO
2257 if ($address['reserved'] == 'yes' or ($numshared + $numreg + $numvirt) > 0)
2258 {
2259 startPortlet ('Allocation');
2260 echo "<table class='widetable' cesspadding=5 cellspacing=0 border=0 align='center'>\n";
2261 echo "<tr><th>Object name</th><th>Interface name</th><th>Interface type</th></tr>\n";
2262 if ( ($numshared > 0 && $numreg > 0) || $numreg > 1 )
2263 $class='trerror';
2264 elseif ( $address['reserved'] == 'yes' and $numshared+$numreg+$numvirt > 0)
2265 $class='trerror';
2266 else
2267 $class='';
e673ee24 2268
59bebe2b
DO
2269 if ($address['reserved'] == 'yes')
2270 echo "<tr class='$class'><td colspan='3'><b>RESERVED</b></td></tr>";
2271 foreach ($address['bonds'] as $bond)
2272 {
2273 echo "<tr class='$class'><td><a href='${root}?page=object&object_id=${bond['object_id']}'>${bond['object_name']}</td><td>${bond['name']}</td><td><b>";
2274 switch ($bond['type'])
2275 {
2276 case 'virtual':
2277 echo "Virtual";
2278 break;
2279 case 'shared':
2280 echo "Shared";
2281 break;
2282 case 'regular':
2283 echo "Regular";
2284 break;
2285 }
2286 echo "</b></td></tr>\n";
2287 }
2288 echo "</table><br><br>";
2289 finishPortlet();
2290 }
e673ee24 2291
59bebe2b 2292 if (count ($address['vslist']))
e673ee24 2293 {
59bebe2b
DO
2294 startPortlet ('Virtual services (' . count ($address['vslist']) . ')');
2295 echo "<table class='widetable' cesspadding=5 cellspacing=0 border=0 align='center'>\n";
2296 echo "<tr><th>VS</th><th>name</th></tr>\n";
2297 foreach ($address['vslist'] as $vsinfo)
e673ee24 2298 {
59bebe2b
DO
2299 echo "<tr><td class=tdleft><a href='${root}?page=vservice&id=${vsinfo['id']}'>";
2300 echo buildVServiceName ($vsinfo) . "</a></td><td class=tdleft>";
5fe1ed76 2301 echo $vsinfo['name'] . "</td></tr>\n";
e673ee24 2302 }
59bebe2b
DO
2303 echo "</table><br><br>";
2304 finishPortlet();
e673ee24 2305 }
5fe1ed76
DO
2306
2307 if (count ($address['rslist']))
2308 {
2309 startPortlet ('Real servers (' . count ($address['rslist']) . ')');
2310 echo "<table class='widetable' cesspadding=5 cellspacing=0 border=0 align='center'>\n";
53f4b619 2311 echo "<tr><th>&nbsp;</th><th>port</th><th>RS pool</th></tr>\n";
5fe1ed76
DO
2312 foreach ($address['rslist'] as $rsinfo)
2313 {
2314 echo "<tr><td>";
2315 if ($rsinfo['inservice'] == 'yes')
2316 printImageHREF ('inservice', 'in service');
2317 else
2318 printImageHREF ('notinservice', 'NOT in service');
c0ae6968 2319 echo "</td><td class=tdleft>${rsinfo['rsport']}</td><td class=tdleft><a href='${root}?page=rspool&pool_id=${rsinfo['pool_id']}'>";
5fe1ed76
DO
2320 echo $rsinfo['poolname'] . "</a></td></tr>\n";
2321 }
2322 echo "</table><br><br>";
2323 finishPortlet();
2324 }
2325
2326
e673ee24
DO
2327// echo "</td><td>";
2328// echo "</td></tr></table>";
2329}
2330
2331function renderIPAddressProperties ()
2332{
2333 global $pageno, $tabno;
2334 $ip = $_REQUEST['ip'];
2335 showMessageOrError();
2336 $address = getIPAddress($ip);
2337 echo "<center><h1>$ip</h1></center>\n";
2338 echo "<table border=0 cellpadding=10 cellpadding=1 align='center'>\n";
2339 echo "<form action='process.php'><input type=hidden name=op value=editAddress>";
2340 echo "<input type=hidden name=page value='${pageno}'>\n";
2341 echo "<input type=hidden name=tab value='${tabno}'>\n";
2342 echo "<input type=hidden name=ip value='${ip}'>";
2343 echo "<tr><td class='tdright'>Name:</td><td class='tdleft'><input type=text name=name size=20 value='".($address['exists']==1?$address['name']:'')."'></tr>";
2344 echo "<td class='tdright'>Reserved:</td><td class='tdleft'><input type=checkbox name=reserved size=20 ".($address['exists']==1?(($address['reserved']=='yes')?'checked':''):'')."></tr>";
2345 echo "<tr><td colspan=2 class='tdcenter'><input type=submit value='Update address'></td></form></tr>";
2346 echo "</table>\n";
2347
2348}
2349
2350function renderIPAddressAssignment ()
2351{
2352 global $pageno, $tabno, $root;
2353 $ip = $_REQUEST['ip'];
2354 $address = getIPAddress($ip);
2355
2356 showMessageOrError();
2357 echo "<center><h1>$ip</h1></center>\n";
2358
2359
2360 echo "<table class='widetable' cesspadding=5 cellspacing=0 border=0 align='center'>\n";
2361 echo "<tr><th>&nbsp;</th><th>Object name</th><th>Interface name</th><th>Interface type</th><th>&nbsp;</th></tr>\n";
2362
2363 $numshared = countRefsOfType($address['bonds'], 'shared', 'eq');
2364 $numreg = countRefsOfType($address['bonds'], 'regular', 'eq');
2365 $numvirt = countRefsOfType($address['bonds'], 'virtual', 'eq');
2366
2367
2368 if ( ($numshared > 0 && $numreg > 0) || $numreg > 1 )
24e85a1a 2369 $class='trerror';
e673ee24 2370 elseif ( $address['reserved'] == 'yes' and $numshared+$numreg+$numvirt > 0)
24e85a1a 2371 $class='trerror';
e673ee24
DO
2372 else
2373 $class='';
2374
2375
2376
2377 if ($address['reserved'] == 'yes')
2378 echo "<tr class='$class'><td colspan='5'><b>RESERVED</b></td></tr>";
2379 foreach ($address['bonds'] as $bond)
2380 {
2381 echo "<tr class='$class'><form action='process.php'>";
2382 echo "<input type=hidden name=op value='editBondForAddress'>";
2383 echo "<input type=hidden name=page value='${pageno}'>";
2384 echo "<input type=hidden name=tab value='${tabno}'>";
2385 echo "<input type=hidden name=ip value='$ip'>";
2386 echo "<input type=hidden name=object_id value='${bond['object_id']}'>";
2387 echo "<td><a href='process.php?op=delIpAssignment&page=${pageno}&tab=${tabno}&ip=$ip&object_id=${bond['object_id']}'>";
2388 printImageHREF ('delete', 'Unallocate address');
2389 echo "</a></td>";
2390 echo "<td><a href='${root}?page=object&object_id=${bond['object_id']}'>${bond['object_name']}</td>";
2391 echo "<td><input type='text' name='bond_name' value='${bond['name']}' size=10></td>";
2392 echo "<td><select name='bond_type'>";
2393 switch ($bond['type'])
2394 {
2395 case 'virtual':
2396 echo "<option value='regular'>Regular</option>";
2397 echo "<option value='virtual' selected>Virtual</option>";
2398 echo "<option value='shared'>Shared</option>";
2399 break;
2400 case 'shared':
2401 echo "<option value='regular'>Regular</option>";
2402 echo "<option value='virtual'>Virtual</option>";
2403 echo "<option value='shared' selected>Shared</option>";
2404 break;
2405 case 'regular':
2406 echo "<option value='regular' selected>Regular</option>";
2407 echo "<option value='virtual'>Virtual</option>";
2408 echo "<option value='shared'>Shared</option>";
2409 break;
2410 }
2411 echo "</select></td><td><input type='submit' value='OK'></td></form></tr>\n";
2412 }
2413 echo "<form action='process.php'><input type='hidden' name='op' value='bindObjectToIp'>";
2414 echo "<input type=hidden name=page value='${pageno}'>\n";
2415 echo "<input type=hidden name=tab value='${tabno}'>\n";
2416 echo "<input type='hidden' name='ip' value='$ip'>";
2417 echo "<td colspan=2><select name='object_id'>";
2418
6dbdc7c7
DO
2419 foreach (explode (',', getConfigVar ('IPV4_PERFORMERS')) as $type)
2420 foreach (getObjectList ($type) as $object)
e673ee24 2421 echo "<option value='${object['id']}'>${object['dname']}</option>";
e673ee24
DO
2422
2423 echo "</select></td><td><input type='text' name='bond_name' value='' size=10></td>";
2424 echo "<td><select name='bond_type'><option value='regular'>Regular</option><option value='virtual'>Virtual</option><option value='shared'>Shared</option></select></td>";
2425 echo "<td><input type='submit' value='Assign address'></td></form></tr>";
2426 echo "</table><br><br>";
2427
2428}
2429
eeb4a5d8 2430function renderNATv4ForObject ($object_id = 0)
e673ee24
DO
2431{
2432 global $pageno, $tabno, $root;
2433
2434 $info = getObjectInfo ($object_id);
eeb4a5d8 2435 $forwards = getNATv4ForObject ($object_id);
e673ee24
DO
2436 $addresses = getObjectAddresses ($object_id);
2437 showMessageOrError();
f28fbe8b 2438 echo "<center><h2>locally performed NAT</h2></center>";
e673ee24
DO
2439
2440 echo "<table class='widetable' cesspadding=5 cellspacing=0 border=0 align='center'>\n";
f28fbe8b 2441 echo "<tr><th></th><th>Match endpoint</th><th>Translate to</th><th>Target object</th><th>Comment</th></tr>\n";
e673ee24
DO
2442
2443 foreach ($forwards['out'] as $pf)
2444 {
24e85a1a 2445 $class='trerror';
e673ee24
DO
2446 $name='';
2447 foreach ($addresses as $addr)
2448 if ($addr['ip'] == $pf['localip'])
2449 {
2450 $class='';
2451 $name = $addr['name'];
2452 break;
2453 }
2454
2455 echo "<tr class='$class'>";
eeb4a5d8 2456 echo "<td><a href='process.php?op=delPortForwarding&localip=${pf['localip']}&localport=${pf['localport']}&remoteip=${pf['remoteip']}&remoteport=${pf['remoteport']}&proto=${pf['proto']}&object_id=$object_id&page=${pageno}&tab=${tabno}'>";
4de22e7e
DO
2457 printImageHREF ('delete', 'Delete NAT rule');
2458 echo "</a></td>";
f28fbe8b
DO
2459 echo "<td>${pf['proto']}/${name}: <a href='${root}?page=ipaddress&tab=default&ip=${pf['localip']}'>${pf['localip']}</a>:${pf['localport']}";
2460 if (!empty ($pf['local_addr_name']))
2461 echo ' (' . $pf['local_addr_name'] . ')';
2462 echo "</td>";
e673ee24
DO
2463 echo "<td><a href='${root}?page=ipaddress&tab=default&ip=${pf['remoteip']}'>${pf['remoteip']}</a>:${pf['remoteport']}</td>";
2464
2465 $address=getIPAddress($pf['remoteip']);
2466
2467 echo "<td class='description'>";
f28fbe8b
DO
2468 if (count ($address['bonds']))
2469 foreach($address['bonds'] as $bond)
2470 echo "<a href='${root}?page=object&tab=default&object_id=${bond['object_id']}'>${bond['object_name']}(${bond['name']})</a> ";
2471 elseif (!empty ($pf['remote_addr_name']))
2472 echo '(' . $pf['remote_addr_name'] . ')';
eeb4a5d8
DO
2473 echo "</td><form action='process.php'><input type='hidden' name='op' value='updPortForwarding'><input type=hidden name=page value='${pageno}'>";
2474 echo "<input type=hidden name=tab value='${tabno}'><input type='hidden' name='object_id' value='$object_id'>";
2475 echo "<input type='hidden' name='localip' value='${pf['localip']}'><input type='hidden' name='localport' value='${pf['localport']}'>";
2476 echo "<input type='hidden' name='remoteip' value='${pf['remoteip']}'><input type='hidden' name='remoteport' value='${pf['remoteport']}'>";
2477 echo "<input type='hidden' name='proto' value='${pf['proto']}'><td class='description'>";
2478 echo "<input type='text' name='description' value='${pf['description']}'> <input type='submit' value='OK'></td></form>";
e673ee24
DO
2479 echo "</tr>";
2480 }
2481 echo "<form action='process.php'><input type='hidden' name='op' value='forwardPorts'>";
2482 echo "<input type='hidden' name='object_id' value='$object_id'>";
2483 echo "<input type=hidden name=page value='${pageno}'>\n";
2484 echo "<input type=hidden name=tab value='${tabno}'>\n";
436605a7 2485 echo "<tr align='center'><td colspan=2>";
eeb4a5d8 2486 printSelect (array ('TCP' => 'TCP', 'UDP' => 'UDP'), 'proto');
52c3543f 2487 echo "<select name='localip' tabindex=1>";
e673ee24
DO
2488
2489 foreach ($addresses as $addr)
09992c16
DO
2490 echo "<option value='${addr['ip']}'>" . (empty ($addr['name']) ? '' : "${addr['name']}: ") .
2491 "${addr['ip']}" . (empty ($addr['address_name']) ? '' : " (${addr['address_name']})") . "</option>";
e673ee24 2492
52c3543f
DO
2493 echo "</select>:<input type='text' name='localport' size='4' tabindex=2></td>";
2494 echo "<td><input type='text' name='remoteip' id='remoteip' size='10' tabindex=3>";
4de22e7e
DO
2495 echo "<a href='javascript:;' onclick='window.open(\"${root}/find_object_ip_helper.php\", \"findobjectip\", \"height=700, width=400, location=no, menubar=no, resizable=yes, scrollbars=no, status=no, titlebar=no, toolbar=no\");'>";
2496 printImageHREF ('find', 'Find object');
2497 echo "</a>";
52c3543f
DO
2498 echo ":<input type='text' name='remoteport' size='4' tabindex=4></td><td></td>";
2499 echo "<td colspan=1><input type='text' name='description' size='20' tabindex=5> <input type='submit' value='Create Forwarding' tabindex=6></td></tr>";
e673ee24
DO
2500 echo "</form>";
2501
2502 echo "</table><br><br>";
2503
f28fbe8b 2504 echo "<center><h2>arriving NAT connections</h2></center>";
e673ee24
DO
2505 echo "<table class='widetable' cesspadding=5 cellspacing=0 border=0 align='center'>\n";
2506 echo "<tr><th></th><th>Source</th><th>Source objects</th><th>Target</th><th>Description</th></tr>\n";
2507
2508 foreach ($forwards['in'] as $pf)
2509 {
eeb4a5d8 2510 echo "<tr><td><a href='process.php?op=delPortForwarding&localip=${pf['localip']}&localport=${pf['localport']}&remoteip=${pf['remoteip']}&remoteport=${pf['remoteport']}&proto=${pf['proto']}&object_id=${pf['object_id']}&page=${pageno}&tab=${tabno}'>";
4de22e7e
DO
2511 printImageHREF ('delete', 'Delete NAT rule');
2512 echo "</a></td>";
e673ee24
DO
2513 echo "<td>${pf['proto']}/<a href='${root}?page=ipaddress&tab=default&ip=${pf['localip']}'>${pf['localip']}</a>:${pf['localport']}</td>";
2514 echo "<td class='description'><a href='${root}?page=object&tab=default&object_id=${pf['object_id']}'>${pf['object_name']}</a>";
2515 echo "</td><td><a href='${root}?page=ipaddress&tab=default&ip=${pf['remoteip']}'>${pf['remoteip']}</a>:${pf['remoteport']}</td>";
2516 echo "<td class='description'>${pf['description']}</td></tr>";
2517 }
2518
e673ee24 2519 echo "</table><br><br>";
e673ee24
DO
2520}
2521
2522
2523function renderAddMultipleObjectsForm ()
2524{
20c901a7 2525 global $root, $pageno, $tabno, $nextorder;
e673ee24
DO
2526
2527 $type_id = array();
7f791d1d 2528 $global_type_id = 0;
e673ee24
DO
2529 $name = array();
2530 $asset_no = array();
2531 $keepvalues = FALSE;
7f791d1d 2532 $log = array();
e673ee24 2533 // Look for current submit.
7f791d1d 2534 if (isset ($_REQUEST['got_fast_data']))
e673ee24
DO
2535 {
2536 $keepvalues = TRUE;
9c0b0016
DO
2537 $max = getConfigVar ('MASSCOUNT');
2538 for ($i = 0; $i < $max; $i++)
e673ee24
DO
2539 {
2540 if (!isset ($_REQUEST["${i}_object_type_id"]))
2541 {
2542 $log[] = array ('code' => 'error', 'message' => "Submitted form is invalid at line " . $i + 1);
2543 break;
2544 }
2c6c7645
DO
2545 assertUIntArg ("${i}_object_type_id", __FUNCTION__, TRUE);
2546 assertStringArg ("${i}_object_name", __FUNCTION__, TRUE);
2547 assertStringArg ("${i}_object_label", __FUNCTION__, TRUE);
2548 assertStringArg ("${i}_object_asset_no", __FUNCTION__, TRUE);
2549 assertStringArg ("${i}_object_barcode", __FUNCTION__, TRUE);
e673ee24
DO
2550 $type_id[$i] = $_REQUEST["${i}_object_type_id"];
2551 // Save user input for possible rendering.
2552 $name[$i] = $_REQUEST["${i}_object_name"];
2553 $label[$i] = $_REQUEST["${i}_object_label"];
2554 $asset_no[$i] = $_REQUEST["${i}_object_asset_no"];
2555 $barcode[$i] = $_REQUEST["${i}_object_barcode"];
2556
2557 // It's better to skip silently than printing a notice.
2558 if ($type_id[$i] == 0)
2559 continue;
2560 if (commitAddObject ($name[$i], $label[$i], $barcode[$i], $type_id[$i], $asset_no[$i]) === TRUE)
2561 $log[] = array ('code' => 'success', 'message' => "Added new object '${name[$i]}'");
2562 else
4d2e93f2 2563 $log[] = array ('code' => 'error', 'message' => __FUNCTION__ . ': commitAddObject() failed');
e673ee24 2564 }
e673ee24 2565 }
7f791d1d
DO
2566 elseif (isset ($_REQUEST['got_very_fast_data']))
2567 {
2568 $keepvalues = TRUE;
2c6c7645
DO
2569 assertUIntArg ('global_type_id', __FUNCTION__, TRUE);
2570 assertStringArg ('namelist', __FUNCTION__, TRUE);
7f791d1d
DO
2571 $global_type_id = $_REQUEST['global_type_id'];
2572 if ($global_type_id == 0)
2573 {
2574 if (!empty ($_REQUEST['namelist']))
2575 $log[] = array ('code' => 'error', 'message' => 'Object type is not selected, check the form below');
2576 else
2577 $log[] = array ('code' => 'error', 'message' => 'Empty form has been ignored. Cheers.');
2578 }
2579 else
2580 {
2581 // The name extractor below was stolen from ophandlers.php:addMultiPorts()
2582 $names1 = explode ('\n', $_REQUEST['namelist']);
2583 $names2 = array();
2584 foreach ($names1 as $line)
2585 {
2586 $parts = explode ('\r', $line);
2587 reset ($parts);
2588 if (empty ($parts[0]))
2589 continue;
2590 else
2591 $names2[] = rtrim ($parts[0]);
2592 }
2593 foreach ($names2 as $cname)
2594 if (commitAddObject ($cname, '', '', $global_type_id, '') === TRUE)
2595 $log[] = array ('code' => 'success', 'message' => "Added new object '${cname}'");
2596 else
2597 $log[] = array ('code' => 'error', 'message' => "Could not add '${cname}'");
2598 }
2599 }
2600 printLog ($log);
e673ee24
DO
2601
2602 // Render a form for the next.
2603 $typelist = getObjectTypeList();
4c330a14 2604 $typelist[0] = 'select type...';
7f791d1d
DO
2605
2606 startPortlet ('Fast way');
20c901a7 2607 echo "<form name=fastform method=post action='${root}?page=${pageno}&tab=${tabno}'>";
e673ee24
DO
2608 echo '<table border=0 align=center>';
2609 echo "<tr><th>Object type</th><th>Common name</th><th>Visible label</th><th>Asset tag</th><th>Barcode</th></tr>\n";
7f791d1d 2610 // If a user forgot to select object type on input, we keep his
e673ee24 2611 // previous input in the form.
9c0b0016
DO
2612 $max = getConfigVar ('MASSCOUNT');
2613 for ($i = 0; $i < $max; $i++)
e673ee24 2614 {
7f791d1d 2615 echo '<tr><td>';
e7ade6bf
DO
2616 // Don't employ DEFAULT_OBJECT_TYPE to avoid creating ghost records for pre-selected empty rows.
2617 printSelect ($typelist, "${i}_object_type_id", 0);
e673ee24
DO
2618 echo '</td>';
2619 echo "<td><input type=text size=30 name=${i}_object_name";
2620 if ($keepvalues and $type_id[$i] == 0)
2621 echo " value='${name[$i]}'";
2622 echo "></td>";
2623 echo "<td><input type=text size=30 name=${i}_object_label";
2624 if ($keepvalues and $type_id[$i] == 0)
2625 echo " value='${label[$i]}'";
2626 echo "></td>";
2627 echo "<td><input type=text size=20 name=${i}_object_asset_no";
2628 if ($keepvalues and $type_id[$i] == 0)
2629 echo " value='${asset_no[$i]}'";
2630 echo "></td>";
2631 echo "<td><input type=text size=10 name=${i}_object_barcode";
2632 if ($keepvalues and $type_id[$i] == 0)
2633 echo " value='${barcode[$i]}'";
2634 echo "></td>";
2635 echo "</tr>\n";
e673ee24 2636 }
7f791d1d 2637 echo "<tr><td class=submit colspan=5><input type=submit name=got_fast_data value='Create'></td></tr>\n";
e673ee24
DO
2638 echo "</form></table>\n";
2639 finishPortlet();
7f791d1d
DO
2640
2641 startPortlet ('Very fast way');
20c901a7 2642 echo "<form name=veryfastform method=post action='${root}?page=${pageno}&tab=${tabno}'>";
7f791d1d 2643 echo 'For each line shown below create an object of type ';
a477e405 2644 printSelect ($typelist, "global_type_id", getConfigVar ('DEFAULT_OBJECT_TYPE'));
7f791d1d
DO
2645 echo " <input type=submit name=got_very_fast_data value='Go!'><br>\n";
2646 echo "<textarea name=namelist cols=40 rows=25>\n";
2647 if ($keepvalues and $global_type_id == 0)
2648 echo $_REQUEST['namelist'];
2649 echo "</textarea></form>\n";
2650 finishPortlet();
e673ee24
DO
2651}
2652
2653function printGreeting ()
2654{
59cd003e 2655 global $remote_username, $accounts, $root;
e673ee24 2656 $account = $accounts[$remote_username];
4eb5efb7 2657 echo "Hello, ${account['user_realname']}. This is RackTables " . CODE_VERSION . ". Click <a href='${root}?logout'>here</a> to logout.";
e673ee24
DO
2658}
2659
2660function renderSearchResults ()
2661{
2662 global $remote_username, $root;
2663 $terms = trim ($_REQUEST['q']);
2664 if (empty ($terms))
2665 {
591ff2c4 2666 showError ('Search string cannot be empty.', __FUNCTION__);
e673ee24
DO
2667 return;
2668 }
2669 if (!authorized ($remote_username, 'object', 'default'))
2670 {
591ff2c4 2671 showError ('You are not authorized for viewing information about objects.', __FUNCTION__);
e673ee24
DO
2672 return;
2673 }
ea5fc465 2674 $nhits = 0;
e673ee24
DO
2675 // If we search for L2 address, we can either find one or find none.
2676 if
2677 (
2678 preg_match ('/^[0-9a-f][0-9a-f]?:[0-9a-f][0-9a-f]?:[0-9a-f][0-9a-f]?:[0-9a-f][0-9a-f]?:[0-9a-f][0-9a-f]?:[0-9a-f][0-9a-f]?$/i', $terms) or
2679 preg_match ('/^[0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f]$/i', $terms) or
ea5fc465
DO
2680 preg_match ('/^[0-9a-f][0-9a-f][0-9a-f][0-9a-f].[0-9a-f][0-9a-f][0-9a-f][0-9a-f].[0-9a-f][0-9a-f][0-9a-f][0-9a-f]$/i', $terms) or
2681 // STP bridge ID: bridge priotity + port MAC address. Cut off first 4 chars and look for MAC address.
2682 preg_match ('/^[0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f]$/i', $terms)
e673ee24
DO
2683 )
2684 // Search for L2 address.
2685 {
ea5fc465 2686 $terms = substr ($terms, -12);
e673ee24
DO
2687 $result = searchByl2address ($terms);
2688 if ($result !== NULL)
2689 {
ea5fc465
DO
2690 $nhits++;
2691 $lasthit = 'port';
2692 $summary['port'][] = $result;
e673ee24 2693 }
e673ee24
DO
2694 }
2695 elseif (preg_match ('/^[0-9][0-9]?[0-9]?\.[0-9]?[0-9]?[0-9]?\.[0-9][0-9]?[0-9]?\.[0-9]?[0-9]?[0-9]?$/i', $terms))
2696 // Search for IP address.
2697 {
2698 $result = getRangeByIp ($terms);
2699 if ($result !== NULL)
2700 {
ea5fc465 2701 $nhits++;
bc3ab23e 2702 $lasthit = 'ipv4address1';
ea5fc465 2703 $summary['ipv4address1'][] = $terms;
e673ee24 2704 }
e673ee24
DO
2705 }
2706 else
ea5fc465 2707 // Search for objects, addresses, networks, virtual services and RS pools by their description.
e673ee24 2708 {
ea5fc465
DO
2709 $tmp = getObjectSearchResults ($terms);
2710 if (count ($tmp))
e673ee24 2711 {
ea5fc465
DO
2712 $nhits += count ($tmp);
2713 $lasthit = 'object';
2714 $summary['object'] = $tmp;
e673ee24 2715 }
ea5fc465
DO
2716 $tmp = getIPv4AddressSearchResult ($terms);
2717 if (count ($tmp))
e673ee24 2718 {
ea5fc465
DO
2719 $nhits += count ($tmp);
2720 $lasthit = 'ipv4address2';
2721 $summary['ipv4address2'] = $tmp;
2722 }
2723 $tmp = getIPv4PrefixSearchResult ($terms);
2724 if (count ($tmp))
2725 {
2726 $nhits += count ($tmp);
2727 $lasthit = 'ipv4network';
2728 $summary['ipv4network'] = $tmp;
2729 }
05411ccd
DO
2730 $tmp = getIPv4RSPoolSearchResult ($terms);
2731 if (count ($tmp))
2732 {
2733 $nhits += count ($tmp);
2734 $lasthit = 'ipv4rspool';
2735 $summary['ipv4rspool'] = $tmp;
2736 }
2737 $tmp = getIPv4VServiceSearchResult ($terms);
2738 if (count ($tmp))
2739 {
2740 $nhits += count ($tmp);
2741 $lasthit = 'ipv4vs';
2742 $summary['ipv4vs'] = $tmp;
2743 }
ea5fc465
DO
2744 }
2745 if ($nhits == 0)
2746 echo "<center><h2>Nothing found for '${terms}'</h2></center>";
2747 elseif ($nhits == 1)
2748 {
2749 $record = current ($summary[$lasthit]);
2750 switch ($lasthit)
2751 {
2752 case 'port':
2753 echo "<script language='Javascript'>document.location='${root}?page=object";
2754 echo "&hl_port_id=" . $record['port_id'];
2755 echo "&object_id=" . $record['object_id'] . "';//</script>";
2756 break;
2757 case 'ipv4address1':
2758 echo "<script language='Javascript'>document.location='${root}?page=ipaddress";
2759 echo "&ip=${record}";
2760 echo "';//</script>";
2761 break;
2762 case 'ipv4address2':
2763 echo "<script language='Javascript'>document.location='${root}?page=ipaddress";
2764 echo "&ip=${record}";
2765 echo "';//</script>";
2766 break;
2767 case 'ipv4network':
2768 echo "<script language='Javascript'>document.location='${root}?page=iprange";
2769 echo "&id=${record['id']}";
2770 echo "';//</script>";
2771 break;
2772 case 'object':
2773 echo "<script language='Javascript'>document.location='${root}?page=object&object_id=${record['id']}';//</script>";
2774 break;
05411ccd
DO
2775 case 'ipv4rspool':
2776 echo "<script language='Javascript'>document.location='${root}?page=rspool&pool_id=${record['pool_id']}';//</script>";
2777 break;
2778 case 'ipv4vs':
2779 echo "<script language='Javascript'>document.location='${root}?page=vservice&id=${record['id']}';//</script>";
2780 break;
ea5fc465
DO
2781 }
2782 return;
2783 }
2784 else
2785 {
2786 global $nextorder;
2787 $order = 'odd';
2788 echo "<center><h2>${nhits} result(s) found for '${terms}'</h2></center>";
2789 foreach ($summary as $where => $what)
2790 switch ($where)
e673ee24 2791 {
ea5fc465
DO
2792 case 'object':
2793 startPortlet ('Objects');
2794 echo '<table border=0 cellpadding=5 cellspacing=0 align=center class=cooltable>';
2795 echo '<tr><th>Common name</th><th>Visible label</th><th>Asset tag</th><th>barcode</th></tr>';
2796 foreach ($what as $obj)
2797 {
2798 echo "<tr class=row_${order}><td><a href=\"${root}?page=object&object_id=${obj['id']}\">${obj['dname']}</a></td>";
2799 echo "<td>${obj['label']}</td>";
2800 echo "<td>${obj['asset_no']}</td>";
2801 echo "<td>${obj['barcode']}</td></tr>";
2802 $order = $nextorder[$order];
2803 }
2804 echo '</table>';
2805 finishPortlet();
2806 break;
2807 case 'ipv4network':
2808 startPortlet ('IPv4 networks');
2809 echo '<table border=0 cellpadding=5 cellspacing=0 align=center class=cooltable>';
2810 echo '<tr><th>Network</th><th>Descritpion</th></tr>';
2811 foreach ($what as $net)
2812 {
2813 echo "<tr class=row_${order}><td class=tdleft><a href='${root}?page=iprange&id=${net['id']}'>${net['ip']}";
2814 echo '/' . $net['mask'] . '</a></td>';
2815 echo "<td class=tdleft>${net['name']}</td></tr>";
2816 $order = $nextorder[$order];
2817 }
2818 echo '</table>';
2819 finishPortlet();
2820 break;
2821 case 'ipv4address2':
2822 startPortlet ('IPv4 addresses');
2823 echo '<table border=0 cellpadding=5 cellspacing=0 align=center class=cooltable>';
2824 echo '<tr><th>Address</th><th>Descritpion</th></tr>';
2825 foreach ($what as $addr)
2826 {
fd190b0a 2827 echo "<tr class=row_${order}><td class=tdleft><a href='${root}?page=ipaddress&ip=${addr['ip']}'>";
ea5fc465
DO
2828 echo "${addr['ip']}</a></td>";
2829 echo "<td class=tdleft>${addr['name']}</td></tr>";
2830 $order = $nextorder[$order];
2831 }
2832 echo '</table>';
2833 finishPortlet();
2834 break;
05411ccd
DO
2835 case 'ipv4rspool':
2836 startPortlet ('RS pools');
2837 echo '<table border=0 cellpadding=5 cellspacing=0 align=center class=cooltable>';
2838 foreach ($what as $rspool)
2839 {
2840 echo "<tr class=row_${order}><td class=tdleft><a href='${root}?page=rspool&pool_id=${rspool['pool_id']}'>";
2841 echo buildRSPoolName ($rspool);
2842 echo "</a></td></tr>";
2843 $order = $nextorder[$order];
2844 }
2845 echo '</table>';
2846 finishPortlet();
2847 break;
2848 case 'ipv4vs':
2849 startPortlet ('Virtual services');
2850 echo '<table border=0 cellpadding=5 cellspacing=0 align=center class=cooltable>';
2851 echo '<tr><th>VS</th><th>Descritpion</th></tr>';
2852 foreach ($what as $vs)
2853 {
2854 echo "<tr class=row_${order}><td class=tdleft><a href='${root}?page=vservice&id=${vs['id']}'>";
2855 echo buildVServiceName ($vs);
2856 echo "</a></td><td>${vs['name']}</td></tr>";
2857 $order = $nextorder[$order];
2858 }
2859 echo '</table>';
2860 finishPortlet();
2861 break;
e673ee24 2862 }
e673ee24
DO
2863 }
2864}
2865
2866// This function prints a table of checkboxes to aid the user in toggling mount atoms
2867// from one state to another. The first argument is rack data as
2868// produced by getRackData(), the second is the value used for the 'unckecked' state
2869// and the third is the value used for 'checked' state.
2870// Usage contexts:
2871// for mounting an object: printAtomGrid ($data, 'F', 'T')
2872// for changing rack design: printAtomGrid ($data, 'A', 'F')
2873// for adding rack problem: printAtomGrid ($data, 'F', 'U')
2874// for adding object problem: printAtomGrid ($data, 'T', 'W')
2875
2876function renderAtomGrid ($data)
2877{
2878 $rack_id = $data['id'];
2879 for ($unit_no = $data['height']; $unit_no > 0; $unit_no--)
2880 {
2881 echo "<tr><th>${unit_no}</th>";
2882 for ($locidx = 0; $locidx < 3; $locidx++)
2883 {
2884 $state = $data[$unit_no][$locidx]['state'];
2885 echo "<td class=state_${state}";
2886 if (isset ($data[$unit_no][$locidx]['hl']))
2887 echo $data[$unit_no][$locidx]['hl'];
2888 echo ">";
2889 if (!($data[$unit_no][$locidx]['enabled'] === TRUE))
2890 echo '<input type=checkbox disabled>';
2891 else
2892 echo "<input type=checkbox" . $data[$unit_no][$locidx]['checked'] . " name=atom_${rack_id}_${unit_no}_${locidx}>";
2893 echo '</td>';
2894 }
2895 echo "</tr>\n";
2896 }
2897}
2898
2899function renderPermissions ()
2900{
2901 startPortlet ('User permissions');
2902 echo "<table class=cooltable border=0 cellpadding=5 cellspacing=0 align=center>\n";
2903 echo "<tr><th>Username</th><th>Page</th><th>Tab</th><th>Access</th></tr>";
2904 global $perms, $nextorder;
2905 $order = 'odd';
2906 foreach ($perms as $username => $pages)
2907 foreach ($pages as $page => $tabs)
2908 foreach ($tabs as $tab => $access)
2909 {
2910 echo "<tr class=row_${order}><td class=tdleft>$username</td><td>$page</td><td>$tab</td><td>$access</td></tr>\n";
2911 $order = $nextorder[$order];
2912 }
2913 echo "</table>\n";
2914 finishPortlet();
2915}
2916
2917function renderAccounts ()
2918{
2919 global $nextorder, $accounts;
2920 startPortlet ('User accounts');
2921 echo "<table class=cooltable border=0 cellpadding=5 cellspacing=0 align=center>\n";
2922 echo "<tr><th class=tdleft>Username</th><th class=tdleft>Real name</th></tr>";
2923 $order = 'odd';
2924 foreach ($accounts as $user)
2925 {
20c901a7
DO
2926 echo "<tr class=row_${order}><td class=tdleft><div title='\$userid_${user['user_id']}'>";
2927 echo "${user['user_name']}</div></td>";
2928 echo "<td class=tdleft>${user['user_realname']}</td></li>";
e673ee24
DO
2929 $order = $nextorder[$order];
2930 }
2931 echo '</table>';
2932 finishPortlet();
2933}
2934
2935function renderAccountsEditForm ()
2936{
2937 global $root, $pageno, $tabno, $accounts;
2938 startPortlet ('User accounts');
2939 showMessageOrError();
2940 echo "<table cellspacing=0 cellpadding=5 align=center class=widetable>\n";
2941 echo "<tr><th>op</th><th>Username</th><th>Real name</th><th>Password</th><th>&nbsp;</th></tr>\n";
2942 foreach ($accounts as $account)
2943 {
2944 echo "<form action='${root}process.php'>";
2945 echo "<input type=hidden name=op value=updateAccount>";
2946 echo "<input type=hidden name=page value='${pageno}'>\n";
2947 echo "<input type=hidden name=tab value='${tabno}'>\n";
2948 echo "<input type=hidden name=id value='${account['user_id']}'><tr>";
2949 echo "<td>";
2950 if ($account['user_enabled'] == 'yes' && $account['user_id'] != 1)
2951 {
2952 echo "<a href='${root}process.php?op=disableAccount&page=${pageno}&tab=${tabno}&id=${account['user_id']}'>";
2953 printImageHREF ('blockuser', 'disable account');
2954 echo "</a>\n";
2955 }
2956 if ($account['user_enabled'] == 'no' && $account['user_id'] != 1)
2957 {
2958 echo "<a href='${root}process.php?op=enableAccount&page=${pageno}&tab=${tabno}&id=${account['user_id']}'>";
2959 printImageHREF ('unblockuser', 'enable account');
2960 echo "</a>\n";
2961 }
2962 // Otherwise skip icon.
2963 echo "</td>";
2964 echo "<td><input type=text name=username value='${account['user_name']}' size=16></td>";
2965 echo "<td><input type=text name=realname value='${account['user_realname']}' size=24></td>";
2966 echo "<td><input type=password name=password value='${account['user_password_hash']}' size=64></td>";
2967 echo "<td><input type='submit' value='OK'></td>";
2968 echo "</form></tr>\n";
2969 }
2970 echo "<form action='${root}process.php' method=post><tr>";
2971 echo "<input type=hidden name=op value=createAccount>\n";
2972 echo "<input type=hidden name=page value='${pageno}'>\n";
2973 echo "<input type=hidden name=tab value='${tabno}'>\n";
2974 echo "<td colspan=2><input type=text size=16 name=username tabindex=100></td>\n";
2975 echo "<td><input type=text size=24 name=realname tabindex=101></td>";
2976 echo "<td><input type=password size=64 name=password tabindex=102></td>";
2977 echo "<td colspan=4><input type=submit value='Create account' tabindex=103></td></tr></form>";
2978 echo "</table><br>\n";
2979 finishPortlet();
2980}
2981
2982function printChildrenAsOptions ($root, $depth = 0)
2983{
2984 echo "<option value=${root['title']}>";
2985 if ($depth == 0)
2986 echo '* ';
2987 for ($i = 0; $i < $depth; $i++)
2988 echo '-- ';
2989 echo $root['title'];
2990 echo "</option>\n";
2991 foreach ($root['kids'] as $kid)
2992 printChildrenAsOptions ($kid, $depth + 1);
2993}
2994
2995// 1. Find all parentless pages.
2996// 2. For each of them recursively find all children.
2997// 3. Output the tree with recursion tree display.
2998function printPagesTree ()
2999{
3000 global $page;
3001 echo '<pre>';
3002 foreach ($page as $ctitle => $cpage)
3003 if (!isset ($cpage['parent']))
3004 {
3005 $croot['title'] = $ctitle;
3006 $croot['kids'] = getAllChildPages ($ctitle);
3007 printChildrenAsOptions ($croot);
3008 }
3009 echo '</pre>';
3010}
3011
3012function renderPermissionsEditForm ()
3013{
3014 global $root, $pageno, $tabno, $perms, $accounts;
3015 startPortlet ('User permissions');
3016 showMessageOrError();
3017 echo "<table cellspacing=0 cellpadding='5' align='center' class='widetable'>\n";
3018 echo "<tr><th>&nbsp;</th><th>Username</th><th>Page</th><th>Tab</th><th>Access</th></tr>\n";
3019 foreach ($perms as $username => $pages)
3020 foreach ($pages as $access_page => $tabs)
3021 foreach ($tabs as $access_tab => $access)
3022 {
3023 echo "<td>";
3024 if ($username != '%')
3025 $userid = $accounts[$username]['user_id'];
3026 else
3027 $userid = 0;
3028 echo "<a href='${root}process.php?op=revoke&page=${pageno}&tab=${tabno}&access_userid=${userid}&access_page=${access_page}&access_tab=${access_tab}'>";
3029 printImageHREF ('revoke', 'Revoke permission');
3030 echo "</a></td>";
3031 echo "<td>${username}</td>";
3032 echo "<td>${access_page}</td>";
3033 echo "<td>${access_tab}</td>";
3034 echo "<td>${access}</td>";
3035 echo "</tr>\n";
3036 }
3037 echo "<form action='${root}process.php' method=post><tr>";
3038 echo "<input type=hidden name=op value=grant>\n";
3039 echo "<input type=hidden name=page value='${pageno}'>\n";
3040 echo "<input type=hidden name=tab value='${tabno}'>\n";
3041 // FIXME: border=0 doesn't work here for unknown reason
3042 echo "<td>";
a5ae8c2a 3043 printImageHREF ('grant', '', TRUE, 103);
e673ee24
DO
3044 echo "</td>";
3045 echo "<td><select name=access_userid>";
3046 echo "<option value=0>ANY</option>";
3047 foreach ($accounts as $account)
3048 echo "<option value=${account['user_id']}>${account['user_name']}</option>";
3049 echo "</select></td>\n";
3050 echo "<td><select name=access_page>";
3051 echo "<option value='%'>ANY</option>";
3052 printPagesTree();
3053 echo "</select></td>";
3054 echo "<td><input type=text size=16 name=access_tab tabindex=102 value=default></td>";
3055 echo "<td><input type=radio name=access_value value=no checked>no <input type=radio name=access_value value=yes>yes</td>";
3056 echo "</tr></form>";
3057 echo "</table><br>\n";
3058 finishPortlet();
3059}
3060
17c32f4c
DO
3061function renderPortMapViewer ()
3062{
3063 renderPortMap (FALSE);
3064}
3065
3066function renderPortMapEditor ()
3067{
3068 renderPortMap (TRUE);
3069}
3070
e673ee24
DO
3071function renderPortMap ($editable = FALSE)
3072{
3073 global $nextorder, $root, $pageno, $tabno;
3074 showMessageOrError();
3075 startPortlet ("Port compatibility map");
3076 $ptlist = getPortTypes();
3077 $pclist = getPortCompat();
3078 $pctable = buildPortCompatMatrixFromList ($ptlist, $pclist);
3079 if ($editable)
3080 {
3081 echo "<form method=post action='${root}process.php'>";
3082 echo "<input type=hidden name=page value='${pageno}'>";
3083 echo "<input type=hidden name=tab value='${tabno}'>";
3084 echo "<input type=hidden name=op value=save>";
3085 }
3086 echo "<table class=cooltable border=0 cellpadding=5 cellspacing=0 align=center>\n";
3087 echo "<tr><th class=vert_th>&nbsp;</th>";
3088 foreach ($ptlist as $name2)
3089 echo "<th>to ${name2}</th>";
3090 echo "</tr>";
3091 // Make a copy to have an independent array pointer.
3092 $ptlistY = $ptlist;
3093 $order = 'odd';
3094 foreach ($ptlistY as $type1 => $name1)
3095 {
3096 echo "<tr class=row_${order}><th class=vert_th style='border-bottom: 0px;'>from $name1</th>";
3097 foreach ($ptlist as $type2 => $name2)
3098 {
3099 echo '<td><input type=checkbox' . ($editable ? " name=atom_${type1}_${type2}" : ' disabled');
3100 echo ($pctable[$type1][$type2] ? ' checked' : '') . '></td>';
3101 }
3102 echo "</tr>\n";
3103 $order = $nextorder[$order];
3104 }
3105 echo '</table><br>';
3106 if ($editable)
3107 {
3108 echo "<input type=submit value='Save changes'>";
3109 echo "</form>";
3110 }
3111 finishPortlet();
3112}
3113
3114function renderConfigMainpage ()
3115{
3116 global $pageno, $root;
3117 $children = getDirectChildPages ($pageno);
3118 echo '<ul>';
27ef67da
DO
3119 // FIXME: assume all config kids to have static titles at the moment,
3120 // but use some proper abstract function later.
e673ee24 3121 foreach ($children as $cpageno => $child)
27ef67da 3122 echo "<li><a href='${root}?page=${cpageno}'>" . $child['title'] . "</li>\n";
e673ee24
DO
3123 echo '';
3124 echo '</ul>';
3125}
3126
3127function renderRackPage ($rack_id)
3128{
3129 if ($rack_id == 0)
3130 {
591ff2c4 3131 showError ('Invalid rack_id', __FUNCTION__);
e673ee24
DO
3132 return;
3133 }
3134 if (($rackData = getRackData ($rack_id)) == NULL)
3135 {
591ff2c4 3136 showError ('getRackData() failed', __FUNCTION__);
e673ee24
DO
3137 return;
3138 }
3139 echo "<table border=0 class=objectview cellspacing=0 cellpadding=0><tr>";
3140
3141 // Left column with information.
3142 echo "<td class=pcleft>";
254673dd 3143 renderRackInfoPortlet ($rackData);
e673ee24
DO
3144 echo '</td>';
3145
3146 // Right column with rendered rack.
3147 echo '<td>';
3148 startPortlet ('Rack diagram');
3149 renderRack ($rack_id);
3150 finishPortlet();
3151 echo '</td>';
3152
3153 echo '</tr></table>';
3154}
3155
3156function renderDictionary ()
3157{
3158 global $nextorder;
2dd59b15 3159 $dict = getDict (TRUE);
aa28ebdf 3160 echo "<br><table class=cooltable border=0 cellpadding=5 cellspacing=0 align=center>\n";
aa28ebdf
DO
3161 foreach ($dict as $chapter_no => $chapter)
3162 {
a22ec5b4 3163 $order = 'odd';
83d2fcca 3164 echo "<tr><th>Chapter</th><th>refs</th><th>Word</th></tr>\n";
aa28ebdf
DO
3165 $wc = count ($chapter['word']);
3166 echo "<tr class=row_${order}><td class=tdleft" . ($wc ? " rowspan = ${wc}" : '');
3167 echo "><div title='number=${chapter_no}'>${chapter['name']} (${wc} records)</div></td>";
3168 if (!$wc)
3169 echo "<td colspan=2>none</td>";
3170 else
e673ee24 3171 {
aa28ebdf
DO
3172 $chap_start = TRUE;
3173 foreach ($chapter['word'] as $key => $value)
3174 {
3175 if (!$chap_start)
3176 echo "<tr class=row_${order}>";
3177 else
3178 $chap_start = FALSE;
6bb8e41d
DO
3179 echo '<td>' . ($chapter['refcnt'][$key] ? $chapter['refcnt'][$key] : '&nbsp;') . '</td>';
3180 echo "<td><div title='key=${key}'>${value}</div></td></tr>\n";
aa28ebdf
DO
3181 $order = $nextorder[$order];
3182 }
e673ee24 3183 }
e673ee24 3184 }
2dd59b15 3185 echo "</table>\n<br>";
e673ee24
DO
3186}
3187
3188function renderDictionaryEditor ()
3189{
f632bd28 3190 global $root, $pageno, $tabno, $nextorder;
e673ee24 3191 $dict = getDict();
95d80773 3192 showMessageOrError();
f632bd28
DO
3193 echo "<br><table class=cooltable border=0 cellpadding=5 cellspacing=0 align=center>\n";
3194 foreach ($dict as $chapter_no => $chapter)
e673ee24 3195 {
f632bd28 3196 $order = 'odd';
b2f9fa84 3197 echo "<tr><th>Chapter</th><th>&nbsp;</th><th>Word</th><th>&nbsp;</th></tr>\n";
f632bd28
DO
3198 $wc = count ($chapter['word']);
3199 // One extra span for the new record per each chapter block.
3200 echo "<tr class=row_${order}><td class=tdleft" . ($wc ? ' rowspan = ' . ($wc + 1) : '');
3201 echo "><div title='number=${chapter_no}'>${chapter['name']} (${wc} records)</div></td>";
3202 echo "<form action='${root}process.php' method=post>";
3203 echo "<input type=hidden name=page value='${pageno}'>";
3204 echo "<input type=hidden name=tab value='${tabno}'>";
3205 echo "<input type=hidden name=op value=add>";
3206 echo "<input type=hidden name=chapter_no value='${chapter['no']}'>";
3207 echo "<td>&nbsp;</td>";
3208 echo "<td class=tdright><input type=text name=dict_value size=32></td>";
95d80773 3209 echo "<td><input type=submit value='Add new'></td>";
f632bd28 3210 echo '</tr></form>';
b2f9fa84 3211 $order = $nextorder[$order];
e673ee24
DO
3212 foreach ($chapter['word'] as $key => $value)
3213 {
3214 echo "<form action='${root}process.php' method=post>";
3215 echo "<input type=hidden name=page value='${pageno}'>";
3216 echo "<input type=hidden name=tab value='${tabno}'>";
3217 echo "<input type=hidden name=op value='upd'>";
3218 echo "<input type=hidden name=chapter_no value='${chapter['no']}'>";
3219 echo "<input type=hidden name=dict_key value='${key}'>";
95d80773 3220 echo "<tr class=row_${order}><td>";
f632bd28
DO
3221 // Prevent deleting words currently used somewhere.
3222 if ($chapter['refcnt'][$key])
b2f9fa84 3223 printImageHREF ('nodelete', 'referenced ' . $chapter['refcnt'][$key] . ' time(s)');
f632bd28
DO
3224 else
3225 {
3226 echo "<a href='${root}process.php?page=${pageno}&tab=${tabno}&op=del&chapter_no=${chapter['no']}&dict_key=${key}'>";
3227 printImageHREF ('delete', 'Delete word');
3228 echo "</a>";
3229 }
3230 echo '</td>';
e673ee24
DO
3231 echo "<td class=tdright><input type=text name=dict_value size=32 value='${value}'></td>";
3232 echo "<td><input type=submit value=OK></td>";
f632bd28
DO
3233 echo "</tr></form>\n";
3234 $order = $nextorder[$order];
3235 } // foreach ($chapter['word']
3236 } // foreach ($dict
3237 echo "</table>\n";
e673ee24
DO
3238}
3239
3240// We don't allow to rename/delete a sticky chapter and we don't allow
3241// to delete a non-empty chapter.
3242function renderChaptersEditor ()
3243{
3244 global $root, $pageno, $tabno;
3245 showMessageOrError();
3246 $dict = getDict();
3247 echo "<table cellspacing=0 cellpadding=5 align=center class=widetable>\n";
3248 echo '<tr><th>&nbsp;</th><th>Chapter name</th><th>Words</th><th>&nbsp;</th></tr>';
3249 foreach ($dict as $chapter)
3250 {
3251 $wordcount = count ($chapter['word']);
3252 $sticky = $chapter['sticky'];
3253 echo "<form action='${root}process.php' method=post>";
3254 echo "<input type=hidden name=page value='${pageno}'>";
3255 echo "<input type=hidden name=tab value='${tabno}'>";
3256 echo "<input type=hidden name=op value=upd>";
3257 echo "<input type=hidden name=chapter_no value='${chapter['no']}'>";
3258 echo '<tr>';
3259 echo '<td>';
0c4605ab
DO
3260 if ($sticky)
3261 printImageHREF ('nodelete', 'system chapter');
3262 elseif ($wordcount > 0)
3263 printImageHREF ('nodelete', 'contains ' . $wordcount . ' word(s)');
e673ee24
DO
3264 else
3265 {
3266 echo "<a href='${root}process.php?page=${pageno}&tab=${tabno}&op=del&chapter_no=${chapter['no']}'>";
3267 printImageHREF ('delete', 'Remove chapter');
3268 echo "</a>";
3269 }
3270 echo '</td>';
3271 echo "<td><input type=text name=chapter_name value='${chapter['name']}'" . ($sticky ? ' disabled' : '') . "></td>";
3272 echo "<td class=tdleft>${wordcount}</td><td>";
3273 if ($sticky)
3274 echo '&nbsp;';
3275 else
3276 echo "<input type=submit value='OK'>";
3277 echo '</td></tr>';
3278 echo '</form>';
3279 }
3280 echo "<form action='${root}process.php' method=post>";
3281 echo "<input type=hidden name=page value='${pageno}'>";
3282 echo "<input type=hidden name=tab value='${tabno}'>";
3283 echo "<input type=hidden name=op value=add>";
3284 echo '<tr><td>';
a5ae8c2a 3285 printImageHREF ('add', '', TRUE);
e673ee24
DO
3286 echo "</td><td colspan=3><input type=text name=chapter_name></td>";
3287 echo '</tr>';
3288 echo '</form>';
3289 echo "</table>\n";
3290}
3291
3292function renderAttributes ()
3293{
3294 global $nextorder;
3295 $attrMap = getAttrMap();
3296 startPortlet ('Optional attributes');
3297 echo "<table class=cooltable border=0 cellpadding=5 cellspacing=0 align=center>\n";
3298 echo "<tr><th class=tdleft>Attribute name</th><th class=tdleft>Attribute type</th><th class=tdleft>Applies to</th></tr>";
3299 $order = 'odd';
3300 foreach ($attrMap as $attr)
3301 {
3302 echo "<tr class=row_${order}>";
3303 echo "<td class=tdleft>${attr['name']}</td>";
3304 echo "<td class=tdleft>${attr['type']}</td>";
3305 echo '<td class=tdleft>';
3306 if (count ($attr['application']) == 0)
3307 echo '&nbsp;';
3308 else
3309 foreach ($attr['application'] as $app)
3310 if ($attr['type'] == 'dict')
3311 echo "${app['objtype_name']} (values from '${app['chapter_name']}')<br>";
3312 else
3313 echo "${app['objtype_name']}<br>";
3314 echo '</td>';
3315 echo "</tr>\n";
3316 $order = $nextorder[$order];
3317 }
3318 echo "</table><br>\n";
3319 finishPortlet();
3320}
3321
3322function renderEditAttributesForm ()
3323{
3324 global $root, $pageno, $tabno;
3325 $attrMap = getAttrMap();
3326 showMessageOrError();
3327 startPortlet ('Optional attributes');
3328 echo "<table cellspacing=0 cellpadding=5 align=center class=widetable>\n";
3329 echo '<tr><th>&nbsp;</th><th>Name</th><th>Type</th><th>&nbsp;</th></tr>';
3330 foreach ($attrMap as $attr)
3331 {
3332 echo "<form action='${root}process.php' method=post>";
3333 echo "<input type=hidden name=page value='${pageno}'>";
3334 echo "<input type=hidden name=tab value='${tabno}'>";
3335 echo "<input type=hidden name=op value=upd>";
3336 echo "<input type=hidden name=attr_id value='${attr['id']}'>";
3337 echo '<tr>';
3338 echo "<td><a href='${root}process.php?page=${pageno}&tab=${tabno}&op=del&attr_id=${attr['id']}'>";
3339 printImageHREF ('delete', 'Remove attribute');
3340 echo '</a></td>';
3341 echo "<td><input type=text name=attr_name value='${attr['name']}'></td>";
3342 echo "<td>${attr['type']}</td>";
3343 echo "<td><input type=submit value='OK'></td>";
3344 echo '</tr>';
3345 echo '</form>';
3346 }
3347 echo "<form action='${root}process.php' method=post>";
3348 echo "<input type=hidden name=page value='${pageno}'>";
3349 echo "<input type=hidden name=tab value='${tabno}'>";
3350 echo "<input type=hidden name=op value=add>";
3351 echo '<tr><td>';
a5ae8c2a 3352 printImageHREF ('add', '', TRUE);
e673ee24
DO
3353 echo "</td><td><input type=text name=attr_name></td>";
3354 echo '<td><select name=attr_type>';
3355 echo '<option value=uint>uint</option>';
3356 echo '<option value=float>float</option>';
3357 echo '<option value=string>string</option>';
3358 echo '<option value=dict>dict</option>';
3359 echo '</select></td>';
3360 echo '</tr>';
3361 echo '</form>';
3362 echo "</table>\n";
3363 finishPortlet();
3364}
3365
3366function renderEditAttrMapForm ()
3367{
3368 global $root, $pageno, $tabno;
3369 $attrMap = getAttrMap();
3370 showMessageOrError();
3371 startPortlet ('Attribute map');
3372 echo "<table cellspacing=0 cellpadding=5 align=center class=widetable>\n";
3373 echo '<tr><th>&nbsp;</th><th>Attribute name</th><th>Object type</th><th>Dictionary chapter</th></tr>';
3374 foreach ($attrMap as $attr)
3375 {
3376 if (count ($attr['application']) == 0)
3377 continue;
3378 foreach ($attr['application'] as $app)
3379 {
3380 echo '<tr>';
3381 echo '<td>';
3382 echo "<a href='${root}process.php?page=${pageno}&tab=${tabno}&op=del&";
3383 echo "attr_id=${attr['id']}&objtype_id=${app['objtype_id']}'>";
3384 printImageHREF ('delete', 'Remove mapping');
3385 echo "</a>";
3386 echo '</td>';
3387 echo "<td>${attr['name']}</td>";
3388 echo "<td>${app['objtype_name']}</td>";
3389 echo "<td>";
3390 if ($attr['type'] == 'dict')
3391 echo "${app['chapter_name']}";
3392 else
3393 echo '&nbsp;';
3394 echo "</td></tr>\n";
3395 }
3396 }
3397 echo "<form action='${root}process.php' method=post>";
3398 echo "<input type=hidden name=page value='${pageno}'>";
3399 echo "<input type=hidden name=tab value='${tabno}'>";
3400 echo "<input type=hidden name=op value=add>";
3401 echo '<tr><td>';
a5ae8c2a 3402 printImageHREF ('add', '', TRUE);
e673ee24
DO
3403 echo "</td><td><select name=attr_id>";
3404 $shortType['uint'] = 'U';
3405 $shortType['float'] = 'F';
3406 $shortType['string'] = 'S';
3407 $shortType['dict'] = 'D';
3408 foreach ($attrMap as $attr)
3409 echo "<option value=${attr['id']}>[" . $shortType[$attr['type']] . "] ${attr['name']}</option>";
3410 echo "</select></td>";
3411 echo '<td>';
3412 printSelect (getObjectTypeList(), 'objtype_id');
3413 echo '</td>';
3414 $dict = getDict();
3415 echo '<td><select name=chapter_no>';
3416 foreach ($dict as $chapter)
3417 if (!$chapter['sticky'])
3418 echo "<option value='${chapter['no']}'>${chapter['name']}</option>";
3419 echo '</select></td>';
3420 echo '</tr>';
3421 echo '</form>';
3422 echo "</table>\n";
3423 finishPortlet();
3424}
3425
a5ae8c2a 3426function printImageHREF ($tag, $title = '', $do_input = FALSE, $tabindex = 0)
e673ee24 3427{
a5ae8c2a
DO
3428 global $root;
3429 $image['error']['path'] = 'pix/error.png';
3430 $image['error']['width'] = 76;
3431 $image['error']['height'] = 17;
a5ae8c2a
DO
3432 $image['logo']['path'] = 'pix/defaultlogo.png';
3433 $image['logo']['width'] = 210;
3434 $image['logo']['height'] = 40;
3435 $image['rackspace']['path'] = 'pix/racks.png';
3436 $image['rackspace']['width'] = 218;
3437 $image['rackspace']['height'] = 200;
3438 $image['objects']['path'] = 'pix/server.png';
3439 $image['objects']['width'] = 218;
3440 $image['objects']['height'] = 200;
3441 $image['ipv4space']['path'] = 'pix/addressspace.png';
3442 $image['ipv4space']['width'] = 218;
3443 $image['ipv4space']['height'] = 200;
f973f491
DO
3444 $image['ipv4slb']['path'] = 'pix/slb.png';
3445 $image['ipv4slb']['width'] = 218;
3446 $image['ipv4slb']['height'] = 200;
a5ae8c2a
DO
3447 $image['config']['path'] = 'pix/configuration.png';
3448 $image['config']['width'] = 218;
3449 $image['config']['height'] = 200;
3450 $image['reports']['path'] = 'pix/report.png';
3451 $image['reports']['width'] = 218;
3452 $image['reports']['height'] = 200;
a5ae8c2a
DO
3453 $image['reserve']['path'] = 'pix/stop.png';
3454 $image['reserve']['width'] = 16;
3455 $image['reserve']['height'] = 16;
3456 $image['useup']['path'] = 'pix/go.png';
3457 $image['useup']['width'] = 16;
3458 $image['useup']['height'] = 16;
3459 $image['blockuser'] = $image['reserve'];
3460 $image['unblockuser'] = $image['useup'];
d48d8820
DO
3461 $image['link']['path'] = 'pix/tango-network-wired.png';
3462 $image['link']['width'] = 16;
3463 $image['link']['height'] = 16;
3464 $image['unlink']['path'] = 'pix/tango-edit-clear.png';
3465 $image['unlink']['width'] = 16;
3466 $image['unlink']['height'] = 16;
77811274 3467 $image['add']['path'] = 'pix/tango-list-add.png';
a5ae8c2a
DO
3468 $image['add']['width'] = 16;
3469 $image['add']['height'] = 16;
d48d8820 3470 $image['delete']['path'] = 'pix/tango-list-remove.png';
a5ae8c2a
DO
3471 $image['delete']['width'] = 16;
3472 $image['delete']['height'] = 16;
0c4605ab
DO
3473 $image['nodelete']['path'] = 'pix/delete_g.png';
3474 $image['nodelete']['width'] = 16;
3475 $image['nodelete']['height'] = 16;
a5ae8c2a
DO
3476 $image['grant'] = $image['add'];
3477 $image['revoke'] = $image['delete'];
d48d8820 3478 $image['inservice']['path'] = 'pix/tango-emblem-system.png';
1f7d18fa
DO
3479 $image['inservice']['width'] = 16;
3480 $image['inservice']['height'] = 16;
d48d8820 3481 $image['notinservice']['path'] = 'pix/tango-dialog-error.png';
1f7d18fa
DO
3482 $image['notinservice']['width'] = 16;
3483 $image['notinservice']['height'] = 16;
77811274 3484 $image['find']['path'] = 'pix/tango-system-search.png';
4de22e7e
DO
3485 $image['find']['width'] = 16;
3486 $image['find']['height'] = 16;
b39e7545
DO
3487 $image['spacer']['path'] = 'pix/pixel.png';
3488 $image['spacer']['width'] = 16;
3489 $image['spacer']['height'] = 16;
9803c56c
DO
3490 $image['next']['path'] = 'pix/tango-go-next.png';
3491 $image['next']['width'] = 32;
3492 $image['next']['height'] = 32;
3493 $image['prev']['path'] = 'pix/tango-go-previous.png';
3494 $image['prev']['width'] = 32;
3495 $image['prev']['height'] = 32;
d48d8820
DO
3496 $image['clear']['path'] = 'pix/tango-edit-clear.png';
3497 $image['clear']['width'] = 16;
3498 $image['clear']['height'] = 16;
e673ee24
DO
3499 if (!isset ($image[$tag]))
3500 $tag = 'error';
3501 $img = $image[$tag];
a5ae8c2a
DO
3502 if ($do_input == TRUE)
3503 echo
3504 "<input type=image name=submit " .
3505 "src='${root}${img['path']}' " .
3506 "border=0 " .
3507 ($tabindex ? '' : "tabindex=${tabindex}") .
3508 ">";
3509 else
3510 echo
3511 "<img " .
3512 "src='${root}${img['path']}' " .
3513 "width=${img['width']} " .
3514 "height=${img['height']} " .
3515 "border=0 " .
3516 (empty ($title) ? '' : "title='${title}'") .
3517 ">";
e673ee24
DO
3518}
3519
3520// This function returns URL for favourite icon.
3521function getFaviconURL ()
3522{
46100c70
DO
3523 global $root;
3524 return $root . 'pix/racktables.ico';
e673ee24
DO
3525}
3526
3527function renderReportSummary ()
3528{
da95280e
DO
3529 echo "<table width='100%'>\n";
3530 echo "<tr><td class=pcleft>\n";
08b4cb24 3531 startPortlet ("Dictionary/objects stats");
da95280e
DO
3532 echo "<table>\n";
3533 foreach (getDictStats() as $header => $data)
7e233246 3534 echo "<tr><th class=tdright>${header}:</th><td class=tdleft>${data}</td></tr>\n";
8948cd63
DO
3535 echo "</table>\n";
3536 finishPortlet();
3537 startPortlet ('IPv4 stats');
3538 echo "<table>\n";
3539 foreach (getIPv4Stats() as $header => $data)
3540 echo "<tr><th class=tdright>${header}:</th><td class=tdleft>${data}</td></tr>\n";
3541 echo "</table>\n";
3542 finishPortlet();
3543 startPortlet ('Rackspace stats');
3544 echo "<table>\n";
3545 foreach (getRackspaceStats() as $header => $data)
3546 echo "<tr><th class=tdright>${header}:</th><td class=tdleft>${data}</td></tr>\n";
da95280e
DO
3547 echo "</table>\n";
3548 finishPortlet();
3549
3550 echo "</td><td class=pcright>\n";
3551
c461c579
DO
3552 startPortlet ("Here be dragons");
3553 dragon();
3554 dragon();
3555 dragon();
3556 echo 'ASCII art &copy; Daniel C. Au';
3557 finishPortlet();
da95280e
DO
3558 echo "</td></tr>\n";
3559 echo "</table>\n";
c461c579
DO
3560}
3561
3562function dragon ()
3563{
3564?>
3565<div class=dragon><pre><font color="#00ff33">
3566 \||/
3567 | <font color="#ff0000">@</font>___oo
3568 /\ /\ / (__<font color=yellow>,,,,</font>|
3569 ) /^\) ^\/ _)
3570 ) /^\/ _)
3571 ) _ / / _)
3572 /\ )/\/ || | )_)
3573 &lt; &gt; |(<font color=white>,,</font>) )__)
3574 || / \)___)\
3575 | \____( )___) )___
3576 \______(_______<font color=white>;;;</font> __<font color=white>;;;</font>
3577
3578</font></pre></div>
3579<?php
e673ee24
DO
3580}
3581
3582function renderUIConfig ()
3583{
4fe32e78
DY
3584 global $configCache, $nextorder;
3585 showMessageOrError();
0a1b1268 3586 startPortlet ('Current configuration');
c461c579
DO
3587 echo '<table class=cooltable border=0 cellpadding=5 cellspacing=0 align=center width="50%">';
3588 echo '<tr><th class=tdleft>Option</th><th class=tdleft>Value</th></tr>';
4fe32e78 3589 $order = 'odd';
0a1b1268 3590 foreach ($configCache as $v)
4fe32e78 3591 {
c461c579
DO
3592 if ($v['is_hidden'] != 'no')
3593 continue;
3594 echo "<tr class=row_${order}>";
3595 echo "<td class=tdright>${v['description']}</td>\n";
3596 echo "<td class=tdleft>${v['varvalue']}</td></tr>";
3597 $order = $nextorder[$order];
4fe32e78 3598 }
0a1b1268
DO
3599 echo "</table>\n";
3600 finishPortlet();
7865c525
DO
3601}
3602
4fe32e78
DY
3603function renderUIConfigEditForm ()
3604{
c461c579 3605 global $root, $pageno, $tabno, $configCache;
4fe32e78
DY
3606 showMessageOrError();
3607 startPortlet ('Current configuration');
c461c579
DO
3608 echo "<table cellspacing=0 cellpadding=5 align=center class=widetable width='50%'>\n";
3609 echo "<tr><th class=tdleft>Option</th>";
3610 echo "<th class=tdleft>Value</th></tr>";
4fe32e78
DY
3611 echo "<form action='${root}process.php'>";
3612 echo "<input type=hidden name=op value='upd'>";
c461c579
DO
3613 echo "<input type=hidden name=page value='${pageno}'>\n";
3614 echo "<input type=hidden name=tab value='${tabno}'>\n";
4fe32e78
DY
3615
3616 $i = 0;
3617 foreach ($configCache as $v)
3618 {
c461c579
DO
3619 if ($v['is_hidden'] != 'no')
3620 continue;
3621 echo "<input type=hidden name=${i}_varname value='${v['varname']}'>";
3622 echo "<tr><td class=tdright>${v['description']}</td>";
3623 echo "<td class=tdleft><input type=text name=${i}_varvalue value='${v['varvalue']}' size=24></td>";
3624 echo "</tr>\n";
3625 $i++;
4fe32e78
DY
3626 }
3627 echo "<input type=hidden name=num_vars value=${i}>\n";
c461c579 3628 echo "<tr><td colspan=2><input type=submit value='Save changes'></td></tr>";
4fe32e78
DY
3629 echo "</form>";
3630 finishPortlet();
3631}
3632
7865c525
DO
3633// This function queries the gateway about current VLAN configuration and
3634// renders a form suitable for submit. Ah, and it does submit processing as well.
111b4a67
DO
3635function renderVLANMembership ($object_id = 0)
3636{
fc8d0004 3637 global $root, $pageno, $tabno, $remote_username;
111b4a67
DO
3638 if ($object_id <= 0)
3639 {
591ff2c4 3640 showError ('Invalid object_id', __FUNCTION__);
111b4a67
DO
3641 return;
3642 }
7865c525
DO
3643
3644 // Handle probable pending