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