r4120 added necessary OB and exceptions wrapping
[racktables] / inc / ophandlers.php
CommitLineData
b325120a 1<?php
e673ee24
DO
2/*
3*
4* This file is a library of operation handlers for RackTables.
5*
6*/
7
08408472
AA
8// This array is deprecated. Please do not add new message constants to it.
9// use the new showError, showWarning, showSuccess functions instead
b6a7d936 10$msgcode = array();
17c32f4c 11
70bbbdc7
DO
12$opspec_list = array();
13
e38cd1da
DO
14$opspec_list['rackspace-edit-addRow'] = array
15(
16 'table' => 'RackRow',
17 'action' => 'INSERT',
18 'arglist' => array
19 (
20 array ('url_argname' => 'name', 'assertion' => 'string')
21 ),
22);
23$opspec_list['rackspace-edit-delete'] = array
24(
25 'table' => 'RackRow',
26 'action' => 'DELETE',
27 'arglist' => array
28 (
29 array ('url_argname' => 'row_id', 'table_colname' => 'id', 'assertion' => 'uint')
30 ),
31);
32$opspec_list['rackspace-edit-updateRow'] = array
33(
34 'table' => 'RackRow',
35 'action' => 'UPDATE',
36 'set_arglist' => array
37 (
38 array ('url_argname' => 'name', 'assertion' => 'string')
39 ),
40 'where_arglist' => array
41 (
42 array ('url_argname' => 'row_id', 'table_colname' => 'id', 'assertion' => 'uint')
43 ),
44);
45$opspec_list['object-ports-delPort'] = array
46(
47 'table' => 'Port',
48 'action' => 'DELETE',
49 'arglist' => array
50 (
51 array ('url_argname' => 'port_id', 'table_colname' => 'id', 'assertion' => 'uint'),
52 array ('url_argname' => 'object_id', 'assertion' => 'uint'),
53 ),
54);
55$opspec_list['object-ports-unlinkPort'] = array
56(
57 'table' => 'Link',
58 'action' => 'DELETE',
59 'arglist' => array
60 (
61 array ('url_argname' => 'port_id', 'table_colname' => 'porta', 'assertion' => 'uint'),
62 array ('url_argname' => 'port_id', 'table_colname' => 'portb', 'assertion' => 'uint'),
63 ),
64 'conjunction' => 'OR',
65);
66$opspec_list['object-log-del'] = array
67(
68 'table' => 'ObjectLog',
69 'action' => 'DELETE',
70 'arglist' => array
71 (
72 array ('url_argname' => 'logid', 'table_colname' => 'id', 'assertion' => 'uint'),
73 array ('url_argname' => 'object_id', 'assertion' => 'uint'),
74 ),
75);
76$opspec_list['ipv4vs-editlblist-delLB'] =
77$opspec_list['ipv4rspool-editlblist-delLB'] =
78$opspec_list['object-editrspvs-delLB'] = array
79(
80 'table' => 'IPv4LB',
81 'action' => 'DELETE',
82 'arglist' => array
83 (
84 array ('url_argname' => 'object_id', 'assertion' => 'uint'),
85 array ('url_argname' => 'pool_id', 'table_colname' => 'rspool_id', 'assertion' => 'uint'),
86 array ('url_argname' => 'vs_id', 'assertion' => 'uint'),
87 ),
88);
89$opspec_list['ipv4net-properties-editRange'] = array
90(
91 'table' => 'IPv4Network',
92 'action' => 'UPDATE',
93 'set_arglist' => array
94 (
95 array ('url_argname' => 'name', 'assertion' => 'string0'),
96 array ('url_argname' => 'comment', 'assertion' => 'string0'),
97 ),
98 'where_arglist' => array
99 (
100 array ('url_argname' => 'id', 'assertion' => 'uint')
101 ),
102);
103$opspec_list['ipv6net-properties-editRange'] = array
104(
105 'table' => 'IPv6Network',
106 'action' => 'UPDATE',
107 'set_arglist' => array
108 (
109 array ('url_argname' => 'name', 'assertion' => 'string0'),
110 array ('url_argname' => 'comment', 'assertion' => 'string0'),
111 ),
112 'where_arglist' => array
113 (
114 array ('url_argname' => 'id', 'assertion' => 'uint')
115 ),
116);
117$opspec_list['ipv4rspool-editrslist-delRS'] = array
118(
119 'table' => 'IPv4RS',
120 'action' => 'DELETE',
121 'arglist' => array
122 (
123 array ('url_argname' => 'id', 'assertion' => 'uint'),
124 ),
125);
126$opspec_list['portmap-edit-add'] = array
127(
128 'table' => 'PortCompat',
129 'action' => 'INSERT',
130 'arglist' => array
131 (
132 array ('url_argname' => 'type1', 'assertion' => 'uint'),
133 array ('url_argname' => 'type2', 'assertion' => 'uint'),
134 ),
135);
136$opspec_list['portmap-edit-del'] = array
137(
138 'table' => 'PortCompat',
139 'action' => 'DELETE',
140 'arglist' => array
141 (
142 array ('url_argname' => 'type1', 'assertion' => 'uint'),
143 array ('url_argname' => 'type2', 'assertion' => 'uint'),
144 ),
145);
146$opspec_list['portifcompat-edit-del'] = array
147(
148 'table' => 'PortInterfaceCompat',
149 'action' => 'DELETE',
150 'arglist' => array
151 (
152 array ('url_argname' => 'iif_id', 'assertion' => 'uint'),
153 array ('url_argname' => 'oif_id', 'assertion' => 'uint'),
154 ),
155);
156$opspec_list['attrs-editmap-del'] = array
157(
158 'table' => 'AttributeMap',
159 'action' => 'DELETE',
160 'arglist' => array
161 (
162 array ('url_argname' => 'attr_id', 'assertion' => 'uint'),
163 array ('url_argname' => 'objtype_id', 'assertion' => 'uint'),
164 ),
165);
166$opspec_list['attrs-editattrs-add'] = array
167(
168 'table' => 'Attribute',
169 'action' => 'INSERT',
170 'arglist' => array
171 (
172 array ('url_argname' => 'attr_type', 'table_colname' => 'type', 'assertion' => 'enum/attr_type'),
173 array ('url_argname' => 'attr_name', 'table_colname' => 'name', 'assertion' => 'string'),
174 ),
175);
176$opspec_list['attrs-editattrs-del'] = array
177(
178 'table' => 'Attribute',
179 'action' => 'DELETE',
180 'arglist' => array
181 (
182 array ('url_argname' => 'attr_id', 'table_colname' => 'id', 'assertion' => 'uint'),
183 ),
184);
185$opspec_list['dict-chapters-add'] = array
186(
187 'table' => 'Chapter',
188 'action' => 'INSERT',
189 'arglist' => array
190 (
191 array ('url_argname' => 'chapter_name', 'table_colname' => 'name', 'assertion' => 'string')
192 ),
193);
194$opspec_list['chapter-edit-add'] = array
195(
196 'table' => 'Dictionary',
197 'action' => 'INSERT',
198 'arglist' => array
199 (
200 array ('url_argname' => 'chapter_no', 'table_colname' => 'chapter_id', 'assertion' => 'uint'),
201 array ('url_argname' => 'dict_value', 'assertion' => 'string'),
202 ),
203);
204$opspec_list['chapter-edit-del'] = array
205(
206 'table' => 'Dictionary',
207 'action' => 'DELETE',
208 'arglist' => array
209 (
210 // Technically dict_key is enough to delete, but including chapter_id into
211 // WHERE clause makes sure, that the action actually happends for the same
212 // chapter, which authorization was granted for.
213 array ('url_argname' => 'chapter_no', 'table_colname' => 'chapter_id', 'assertion' => 'uint'),
214 array ('url_argname' => 'dict_key', 'assertion' => 'uint'),
215 ),
216);
217$opspec_list['tagtree-edit-createTag'] = array
218(
219 'table' => 'TagTree',
220 'action' => 'INSERT',
221 'arglist' => array
222 (
223 array ('url_argname' => 'tag_name', 'table_colname' => 'tag', 'assertion' => 'tag'),
224 array ('url_argname' => 'parent_id', 'assertion' => 'uint0', 'if_empty' => 'NULL'),
225 ),
226);
227$opspec_list['tagtree-edit-destroyTag'] = array
228(
229 'table' => 'TagTree',
230 'action' => 'DELETE',
231 'arglist' => array
232 (
c59a986c
DO
233 array ('url_argname' => 'tag_id', 'table_colname' => 'id', 'assertion' => 'uint'),
234 ),
235);
236$opspec_list['tagtree-edit-updateTag'] = array
237(
238 'table' => 'TagTree',
239 'action' => 'UPDATE',
240 'set_arglist' => array
241 (
242 array ('url_argname' => 'tag_name', 'table_colname' => 'tag', 'assertion' => 'tag'),
243 array ('url_argname' => 'parent_id', 'assertion' => 'uint0', 'if_empty' => 'NULL'),
244 ),
245 'where_arglist' => array
246 (
247 array ('url_argname' => 'tag_id', 'table_colname' => 'id', 'assertion' => 'uint'),
e38cd1da
DO
248 ),
249);
250$opspec_list['vlandomain-vlanlist-add'] = array
251(
252 'table' => 'VLANDescription',
253 'action' => 'INSERT',
254 'arglist' => array
255 (
256 array ('url_argname' => 'vdom_id', 'table_colname' => 'domain_id', 'assertion' => 'uint'),
257 array ('url_argname' => 'vlan_id', 'assertion' => 'uint'),
258 array ('url_argname' => 'vlan_type', 'assertion' => 'enum/vlan_type'),
259 array ('url_argname' => 'vlan_descr', 'assertion' => 'string0', 'if_empty' => 'NULL'),
260 ),
261);
262
08408472
AA
263// This function is DEPRECATED. Show messages through showError and showSuccess,
264// you dont need to return anything from an ophandler to redirect user back to the page containing submit form
265function buildWideRedirectURL ($log = NULL, $nextpage = NULL, $nexttab = NULL, $moreArgs = array())
17c32f4c 266{
790a60e8 267 global $page, $pageno, $tabno;
b6a7d936
DO
268 if ($nextpage === NULL)
269 $nextpage = $pageno;
270 if ($nexttab === NULL)
271 $nexttab = $tabno;
790a60e8 272 $url = "index.php?page=${nextpage}&tab=${nexttab}";
b6a7d936
DO
273 if (isset ($page[$nextpage]['bypass']))
274 $url .= '&' . $page[$nextpage]['bypass'] . '=' . $_REQUEST[$page[$nextpage]['bypass']];
17c32f4c 275
b6a7d936 276 if (count($moreArgs)>0)
17c32f4c 277 {
b6a7d936
DO
278 foreach($moreArgs as $arg=>$value)
279 {
280 if (gettype($value) == 'array')
281 {
282 foreach ($value as $v)
283 {
284 $url .= '&'.urlencode($arg.'[]').'='.urlencode($v);
285 }
286 }
287 else
288 $url .= '&'.urlencode($arg).'='.urlencode($value);
289 }
17c32f4c 290 }
b6a7d936 291
08408472
AA
292 if (! empty ($log))
293 {
294 if (empty ($_SESSION['log']))
295 $_SESSION['log'] = $log;
296 elseif ($_SESSION['log']['v'] == $log['v'])
297 $_SESSION['log'] = array_merge_recursive($log, $_SESSION['log']);
298 elseif ($log['v'] == 1 and $_SESSION['log']['v'] == 2)
299 foreach ($log['m'] as $msg)
300 setMessage($msg['message'], $msg['code'], FALSE);
301 elseif ($log['v'] == 2 and $_SESSION['log']['v'] == 1)
302 {
303 foreach ($_SESSION['log'] as $msg)
304 {
305 if (! is_array ($msg))
306 continue;
307 var_dump ($msg);
308 $new_v2_item = array('c' => '', 'a' => array());
309 switch ($msg['code'])
310 {
311 case 'error':
312 $new_v2_item['c'] = 100;
313 break;
314 case 'success':
315 $new_v2_item['c'] = 0;
316 break;
317 case 'warning':
318 $new_v2_item['c'] = 200;
319 break;
320 default:
321 $new_v2_item['c'] = 300;
322 }
323 $new_v2_item['a'][] = $msg['message'];
324 $log['m'][] = $new_v2_item;
325 }
326 $_SESSION['log'] = $log; // substitute v1 log structure with merged v2
327 }
328 }
b6a7d936 329 return $url;
17c32f4c
DO
330}
331
08408472
AA
332// This function is DEPRECATED. Show messages through showError and showSuccess,
333// you dont need to return anything from an ophandler to redirect user back to the page containing submit form
05d3c190 334function buildRedirectURL ($callfunc, $status, $log_args = array(), $nextpage = NULL, $nexttab = NULL, $url_args = array())
17c32f4c 335{
b6a7d936
DO
336 global $pageno, $tabno, $msgcode;
337 if ($nextpage === NULL)
338 $nextpage = $pageno;
339 if ($nexttab === NULL)
340 $nexttab = $tabno;
05d3c190 341 return buildWideRedirectURL (oneLiner ($msgcode[$callfunc][$status], $log_args), $nextpage, $nexttab, $url_args);
17c32f4c
DO
342}
343
00e93d63 344$msgcode['addPortForwarding']['OK'] = 48;
b6a7d936 345$msgcode['addPortForwarding']['ERR'] = 100;
e673ee24
DO
346function addPortForwarding ()
347{
0cc24e9a
DY
348 assertUIntArg ('object_id');
349 assertIPv4Arg ('localip');
350 assertIPv4Arg ('remoteip');
351 assertUIntArg ('localport');
352 assertStringArg ('proto');
353 assertStringArg ('description', TRUE);
103b1e1e 354 $remoteport = isset ($_REQUEST['remoteport']) ? $_REQUEST['remoteport'] : '';
59a83bd8 355 if (!strlen ($remoteport))
f75eb878 356 $remoteport = $_REQUEST['localport'];
e673ee24 357
9bea3a8b
DO
358 $error = newPortForwarding
359 (
103b1e1e 360 $_REQUEST['object_id'],
9bea3a8b
DO
361 $_REQUEST['localip'],
362 $_REQUEST['localport'],
363 $_REQUEST['remoteip'],
364 $remoteport,
365 $_REQUEST['proto'],
366 $_REQUEST['description']
367 );
e673ee24
DO
368
369 if ($error == '')
135080d8 370 return buildRedirectURL (__FUNCTION__, 'OK');
e673ee24 371 else
135080d8 372 return buildRedirectURL (__FUNCTION__, 'ERR', array ($error));
e673ee24
DO
373}
374
00e93d63 375$msgcode['delPortForwarding']['OK'] = 49;
a5c589d2 376$msgcode['delPortForwarding']['ERR'] = 111;
e673ee24
DO
377function delPortForwarding ()
378{
0cc24e9a
DY
379 assertUIntArg ('object_id');
380 assertIPv4Arg ('localip');
381 assertIPv4Arg ('remoteip');
382 assertUIntArg ('localport');
383 assertUIntArg ('remoteport');
384 assertStringArg ('proto');
e673ee24 385
a5c589d2 386 $result = deletePortForwarding
103b1e1e
DO
387 (
388 $_REQUEST['object_id'],
389 $_REQUEST['localip'],
390 $_REQUEST['localport'],
391 $_REQUEST['remoteip'],
392 $_REQUEST['remoteport'],
393 $_REQUEST['proto']
394 );
a5c589d2 395 buildRedirectURL (__FUNCTION__, $result !== FALSE ? 'OK' : 'ERR');
e673ee24
DO
396}
397
00e93d63 398$msgcode['updPortForwarding']['OK'] = 51;
a5c589d2 399$msgcode['updPortForwarding']['ERR'] = 109;
e673ee24
DO
400function updPortForwarding ()
401{
0cc24e9a
DY
402 assertUIntArg ('object_id');
403 assertIPv4Arg ('localip');
404 assertIPv4Arg ('remoteip');
405 assertUIntArg ('localport');
406 assertUIntArg ('remoteport');
407 assertStringArg ('proto');
408 assertStringArg ('description');
e673ee24 409
a5c589d2 410 $result = updatePortForwarding
103b1e1e
DO
411 (
412 $_REQUEST['object_id'],
413 $_REQUEST['localip'],
414 $_REQUEST['localport'],
415 $_REQUEST['remoteip'],
416 $_REQUEST['remoteport'],
417 $_REQUEST['proto'],
418 $_REQUEST['description']
419 );
a5c589d2 420 buildRedirectURL (__FUNCTION__, $result !== FALSE ? 'OK' : 'ERR');
e673ee24
DO
421}
422
00e93d63 423$msgcode['addPortForObject']['OK'] = 48;
b6a7d936
DO
424$msgcode['addPortForObject']['ERR1'] = 101;
425$msgcode['addPortForObject']['ERR2'] = 100;
e673ee24
DO
426function addPortForObject ()
427{
0cc24e9a 428 assertStringArg ('port_name', TRUE);
9b6e7bd1 429 genericAssertion ('port_l2address', 'l2address0');
59a83bd8 430 if (!strlen ($_REQUEST['port_name']))
135080d8 431 return buildRedirectURL (__FUNCTION__, 'ERR1');
6405ecd3
DO
432 $error = commitAddPort
433 (
434 $_REQUEST['object_id'],
435 trim ($_REQUEST['port_name']),
436 $_REQUEST['port_type_id'],
437 trim ($_REQUEST['port_label']),
438 trim ($_REQUEST['port_l2address'])
439 );
103b1e1e 440 if ($error != '')
135080d8 441 return buildRedirectURL (__FUNCTION__, 'ERR2', array ($error));
e673ee24 442 else
135080d8 443 return buildRedirectURL (__FUNCTION__, 'OK', array ($_REQUEST['port_name']));
e673ee24
DO
444}
445
00e93d63 446$msgcode['editPortForObject']['OK'] = 7;
b6a7d936
DO
447$msgcode['editPortForObject']['ERR1'] = 101;
448$msgcode['editPortForObject']['ERR2'] = 100;
e673ee24
DO
449function editPortForObject ()
450{
0cc24e9a
DY
451 assertUIntArg ('port_id');
452 assertUIntArg ('port_type_id');
e8acfc2d 453 assertStringArg ('reservation_comment', TRUE);
9b6e7bd1 454 genericAssertion ('l2address', 'l2address0');
d0a69ce8 455 // tolerate empty value now to produce custom informative message later
0cc24e9a 456 assertStringArg ('name', TRUE);
59a83bd8 457 if (!strlen ($_REQUEST['name']))
135080d8 458 return buildRedirectURL (__FUNCTION__, 'ERR1');
103b1e1e 459
e8acfc2d 460 $error = commitUpdatePort ($_REQUEST['object_id'], $_REQUEST['port_id'], $_REQUEST['name'], $_REQUEST['port_type_id'], $_REQUEST['label'], $_REQUEST['l2address'], $_REQUEST['reservation_comment']);
103b1e1e 461 if ($error != '')
135080d8 462 return buildRedirectURL (__FUNCTION__, 'ERR2', array ($error));
e673ee24 463 else
135080d8 464 return buildRedirectURL (__FUNCTION__, 'OK', array ($_REQUEST['name']));
e673ee24
DO
465}
466
b6a7d936
DO
467$msgcode['linkPortForObject']['OK'] = 8;
468$msgcode['linkPortForObject']['ERR'] = 100;
e673ee24
DO
469function linkPortForObject ()
470{
0cc24e9a
DY
471 assertUIntArg ('port_id');
472 assertUIntArg ('remote_port_id');
0c7c9f8b 473 assertStringArg ('cable', TRUE);
e673ee24 474
cd3775e9 475 // FIXME: ensure, that at least one of these ports belongs to the current object
0c7c9f8b 476 $error = linkPorts ($_REQUEST['port_id'], $_REQUEST['remote_port_id'], $_REQUEST['cable']);
e673ee24 477 if ($error != '')
135080d8 478 return buildRedirectURL (__FUNCTION__, 'ERR', array ($error));
d0dadd80
DO
479 global $sic;
480 $local_port_info = getPortInfo ($sic['port_id']);
481 $remote_port_info = getPortInfo ($sic['remote_port_id']);
cd3775e9
DO
482 $remote_object = spotEntity ('object', $remote_port_info['object_id']);
483 return buildRedirectURL
484 (
485 __FUNCTION__,
486 'OK',
487 array
488 (
489 $local_port_info['name'],
490 $remote_port_info['name'],
491 $remote_object['dname'],
492 )
493 );
e673ee24
DO
494}
495
b6a7d936
DO
496$msgcode['addMultiPorts']['OK'] = 10;
497$msgcode['addMultiPorts']['ERR'] = 123;
e673ee24
DO
498function addMultiPorts ()
499{
0cc24e9a
DY
500 assertStringArg ('format');
501 assertStringArg ('input');
ff0eaf57 502 assertStringArg ('port_type');
e673ee24
DO
503 $format = $_REQUEST['format'];
504 $port_type = $_REQUEST['port_type'];
505 $object_id = $_REQUEST['object_id'];
506 // Input lines are escaped, so we have to explode and to chop by 2-char
507 // \n and \r respectively.
7f42d792 508 $lines1 = explode ("\n", $_REQUEST['input']);
e673ee24
DO
509 foreach ($lines1 as $line)
510 {
511 $parts = explode ('\r', $line);
512 reset ($parts);
59a83bd8 513 if (!strlen ($parts[0]))
e673ee24
DO
514 continue;
515 else
516 $lines2[] = rtrim ($parts[0]);
517 }
518 $ports = array();
519 foreach ($lines2 as $line)
520 {
521 switch ($format)
522 {
523 case 'fisxii':
84986395 524 $words = explode (' ', preg_replace ('/[[:space:]]+/', ' ', $line));
e673ee24
DO
525 list ($slot, $port) = explode ('/', $words[0]);
526 $ports[] = array
527 (
528 'name' => "e ${slot}/${port}",
529 'l2address' => $words[8],
530 'label' => "slot ${slot} port ${port}"
531 );
532 break;
533 case 'c3600asy':
84986395 534 $words = explode (' ', preg_replace ('/[[:space:]]+/', ' ', trim (substr ($line, 3))));
e673ee24
DO
535/*
536How Async Lines are Numbered in Cisco 3600 Series Routers
537http://www.cisco.com/en/US/products/hw/routers/ps274/products_tech_note09186a00801ca70b.shtml
538
539Understanding 16- and 32-Port Async Network Modules
540http://www.cisco.com/en/US/products/hw/routers/ps274/products_tech_note09186a00800a93f0.shtml
541*/
542 $async = $words[0];
543 $slot = floor (($async - 1) / 32);
544 $octalgroup = floor (($async - 1 - $slot * 32) / 8);
545 $cable = $async - $slot * 32 - $octalgroup * 8;
546 $og_label[0] = 'async 0-7';
547 $og_label[1] = 'async 8-15';
548 $og_label[2] = 'async 16-23';
549 $og_label[3] = 'async 24-31';
550 $ports[] = array
551 (
552 'name' => "async ${async}",
553 'l2address' => '',
554 'label' => "slot ${slot} " . $og_label[$octalgroup] . " cable ${cable}"
555 );
556 break;
557 case 'fiwg':
84986395 558 $words = explode (' ', preg_replace ('/[[:space:]]+/', ' ', $line));
e673ee24
DO
559 $ifnumber = $words[0] * 1;
560 $ports[] = array
561 (
562 'name' => "e ${ifnumber}",
563 'l2address' => "${words[8]}",
564 'label' => "${ifnumber}"
565 );
566 break;
351d4dbf 567 case 'ssv1':
5b585342 568 $words = explode (' ', $line);
59a83bd8 569 if (!strlen ($words[0]) or !strlen ($words[1]))
351d4dbf
DO
570 continue;
571 $ports[] = array
572 (
573 'name' => $words[0],
574 'l2address' => $words[1],
575 'label' => ''
576 );
577 break;
e673ee24 578 default:
135080d8 579 return buildRedirectURL (__FUNCTION__, 'ERR');
e673ee24
DO
580 break;
581 }
582 }
583 // Create ports, if they don't exist.
584 $added_count = $updated_count = $error_count = 0;
585 foreach ($ports as $port)
586 {
e9d357e1
DO
587 $port_ids = getPortIDs ($object_id, $port['name']);
588 if (!count ($port_ids))
e673ee24
DO
589 {
590 $result = commitAddPort ($object_id, $port['name'], $port_type, $port['label'], $port['l2address']);
591 if ($result == '')
592 $added_count++;
593 else
594 $error_count++;
595 }
e9d357e1 596 elseif (count ($port_ids) == 1) // update only single-socket ports
e673ee24 597 {
e9d357e1 598 $result = commitUpdatePort ($object_id, $port_ids[0], $port['name'], $port_type, $port['label'], $port['l2address']);
e673ee24
DO
599 if ($result == '')
600 $updated_count++;
601 else
602 $error_count++;
603 }
604 }
135080d8 605 return buildRedirectURL (__FUNCTION__, 'OK', array ($added_count, $updated_count, $error_count));
e673ee24
DO
606}
607
a1fc539a 608$msgcode['addBulkPorts']['OK'] = 82;
a1fc539a
RF
609function addBulkPorts ()
610{
647635ad
DO
611 assertStringArg ('port_type_id');
612 assertStringArg ('port_name');
613 assertStringArg ('port_label', TRUE);
329aa3e5 614 assertUIntArg ('port_numbering_start', TRUE);
647635ad 615 assertUIntArg ('port_numbering_count');
a1fc539a
RF
616
617 $object_id = $_REQUEST['object_id'];
618 $port_name = $_REQUEST['port_name'];
619 $port_type_id = $_REQUEST['port_type_id'];
620 $port_label = $_REQUEST['port_label'];
621 $port_numbering_start = $_REQUEST['port_numbering_start'];
622 $port_numbering_count = $_REQUEST['port_numbering_count'];
623
a1fc539a
RF
624 $added_count = $error_count = 0;
625 if(strrpos($port_name, "%u") === false )
626 $port_name .= '%u';
2b5a8c1b 627 for ($i=0,$c=$port_numbering_start; $i<$port_numbering_count; $i++,$c++)
a1fc539a 628 {
2b5a8c1b 629 $result = commitAddPort ($object_id, @sprintf($port_name,$c), $port_type_id, @sprintf($port_label,$c), '');
a1fc539a
RF
630 if ($result == '')
631 $added_count++;
632 else
633 $error_count++;
634 }
635 return buildRedirectURL (__FUNCTION__, 'OK', array ($added_count, $error_count));
636}
637
00e93d63 638$msgcode['updIPv4Allocation']['OK'] = 51;
32832c0e 639$msgcode['updIPv4Allocation']['ERR'] = 109;
b4c1ef87 640function updIPv4Allocation ()
e673ee24 641{
0cc24e9a
DY
642 assertIPv4Arg ('ip');
643 assertUIntArg ('object_id');
644 assertStringArg ('bond_name', TRUE);
96597d19 645 genericAssertion ('bond_type', 'enum/inet4alloc');
e673ee24 646
32832c0e
DO
647 $result = updateBond ($_REQUEST['ip'], $_REQUEST['object_id'], $_REQUEST['bond_name'], $_REQUEST['bond_type']);
648 return buildRedirectURL (__FUNCTION__, $result === FALSE ? 'ERR' : 'OK');
e673ee24
DO
649}
650
00e93d63 651$msgcode['updIPv6Allocation']['OK'] = 51;
21ee3351
AA
652$msgcode['updIv6PAllocation']['ERR'] = 109;
653function updIPv6Allocation ()
654{
655 $ipv6 = assertIPv6Arg ('ip');
656 assertUIntArg ('object_id');
657 assertStringArg ('bond_name', TRUE);
96597d19 658 genericAssertion ('bond_type', 'enum/inet6alloc');
21ee3351
AA
659
660 $result = updateIPv6Bond ($ipv6, $_REQUEST['object_id'], $_REQUEST['bond_name'], $_REQUEST['bond_type']);
661 return buildRedirectURL (__FUNCTION__, $result === FALSE ? 'ERR' : 'OK');
662}
663
00e93d63 664$msgcode['delIPv4Allocation']['OK'] = 49;
32832c0e 665$msgcode['delIPv4Allocation']['ERR'] = 111;
b4c1ef87 666function delIPv4Allocation ()
e673ee24 667{
0cc24e9a
DY
668 assertIPv4Arg ('ip');
669 assertUIntArg ('object_id');
e673ee24 670
32832c0e
DO
671 $result = unbindIpFromObject ($_REQUEST['ip'], $_REQUEST['object_id']);
672 return buildRedirectURL (__FUNCTION__, $result === FALSE ? 'ERR' : 'OK');
e673ee24
DO
673}
674
00e93d63 675$msgcode['delIPv6Allocation']['OK'] = 49;
21ee3351
AA
676$msgcode['delIPv6Allocation']['ERR'] = 111;
677function delIPv6Allocation ()
678{
679 assertUIntArg ('object_id');
680 $ipv6 = assertIPv6Arg ('ip');
681 $result = unbindIPv6FromObject ($ipv6, $_REQUEST['object_id']);
682 return buildRedirectURL (__FUNCTION__, $result === FALSE ? 'ERR' : 'OK');
683}
684
00e93d63 685$msgcode['addIPv4Allocation']['OK'] = 48;
b6a7d936
DO
686$msgcode['addIPv4Allocation']['ERR1'] = 170;
687$msgcode['addIPv4Allocation']['ERR2'] = 100;
b4c1ef87 688function addIPv4Allocation ()
e673ee24 689{
0cc24e9a
DY
690 assertIPv4Arg ('ip');
691 assertUIntArg ('object_id');
692 assertStringArg ('bond_name', TRUE);
96597d19 693 genericAssertion ('bond_type', 'enum/inet4alloc');
da958e52 694
b4c1ef87 695 // Strip masklen.
84986395 696 $ip = preg_replace ('@/[[:digit:]]+$@', '', $_REQUEST['ip']);
2be3fd23 697 if (getConfigVar ('IPV4_JAYWALK') != 'yes' and NULL === getIPv4AddressNetworkId ($ip))
135080d8 698 return buildRedirectURL (__FUNCTION__, 'ERR1', array ($ip));
5222f192 699
fc2e1602 700 if (FALSE === bindIpToObject ($ip, $_REQUEST['object_id'], $_REQUEST['bond_name'], $_REQUEST['bond_type']))
135080d8 701 return buildRedirectURL (__FUNCTION__, 'ERR2', array ($error));
53ef3908 702 $address = getIPv4Address ($ip);
59a83bd8 703 if ($address['reserved'] == 'yes' or strlen ($address['name']))
b4c1ef87
DO
704 {
705 $release = getConfigVar ('IPV4_AUTO_RELEASE');
706 if ($release >= 1)
707 $address['reserved'] = 'no';
708 if ($release >= 2)
709 $address['name'] = '';
710 updateAddress ($ip, $address['name'], $address['reserved']);
711 }
135080d8 712 return buildRedirectURL (__FUNCTION__, 'OK');
e673ee24
DO
713}
714
00e93d63 715$msgcode['addIPv6Allocation']['OK'] = 48;
21ee3351
AA
716$msgcode['addIPv6Allocation']['ERR1'] = 170;
717$msgcode['addIPv6Allocation']['ERR2'] = 100;
718function addIPv6Allocation ()
719{
720 assertUIntArg ('object_id');
721 assertStringArg ('bond_name', TRUE);
96597d19 722 genericAssertion ('bond_type', 'enum/inet6alloc');
21ee3351
AA
723
724 // Strip masklen.
725 $ipv6 = new IPv6Address;
726 if (! $ipv6->parse (preg_replace ('@/\d+$@', '', $_REQUEST['ip'])))
727 throw new InvalidRequestArgException('ip', $_REQUEST['ip'], 'parameter is not a valid ipv6 address');
728
729 if (getConfigVar ('IPV4_JAYWALK') != 'yes' and NULL === getIPv6AddressNetworkId ($ipv6))
730 return buildRedirectURL (__FUNCTION__, 'ERR1', array ($ip));
731
732 if (FALSE === bindIPv6ToObject ($ipv6, $_REQUEST['object_id'], $_REQUEST['bond_name'], $_REQUEST['bond_type']))
733 return buildRedirectURL (__FUNCTION__, 'ERR2', array ($error));
734 $address = getIPv6Address ($ipv6);
735 if ($address['reserved'] == 'yes' or strlen ($address['name']))
736 {
737 $release = getConfigVar ('IPV4_AUTO_RELEASE');
738 if ($release >= 1)
739 $address['reserved'] = 'no';
740 if ($release >= 2)
741 $address['name'] = '';
742 updateAddress ($ipv6, $address['name'], $address['reserved']);
743 }
744 return buildRedirectURL (__FUNCTION__, 'OK');
745}
746
00e93d63 747$msgcode['addIPv4Prefix']['OK'] = 48;
b6a7d936 748$msgcode['addIPv4Prefix']['ERR'] = 100;
42023f03 749function addIPv4Prefix ()
e673ee24 750{
0cc24e9a
DY
751 assertStringArg ('range');
752 assertStringArg ('name', TRUE);
e673ee24 753
fa05e3de
DO
754 $is_bcast = isset ($_REQUEST['is_bcast']) ? $_REQUEST['is_bcast'] : 'off';
755 $taglist = isset ($_REQUEST['taglist']) ? $_REQUEST['taglist'] : array();
357eb2ea
DO
756 global $sic;
757 $error = createIPv4Prefix ($_REQUEST['range'], $sic['name'], $is_bcast == 'on', $taglist);
e673ee24 758 if ($error != '')
135080d8 759 return buildRedirectURL (__FUNCTION__, 'ERR', array ($error));
e673ee24 760 else
135080d8 761 return buildRedirectURL (__FUNCTION__, 'OK');
e673ee24
DO
762}
763
00e93d63 764$msgcode['addIPv6Prefix']['OK'] = 48;
21ee3351 765$msgcode['addIPv6Prefix']['ERR'] = 100;
21ee3351
AA
766function addIPv6Prefix ()
767{
768 assertStringArg ('range');
769 assertStringArg ('name', TRUE);
770
771 $taglist = isset ($_REQUEST['taglist']) ? $_REQUEST['taglist'] : array();
772 global $sic;
773 $error = createIPv6Prefix ($_REQUEST['range'], $sic['name'], $taglist);
774 if ($error != '')
775 return buildRedirectURL (__FUNCTION__, 'ERR', array ($error));
776 else
777 return buildRedirectURL (__FUNCTION__, 'OK');
778}
779
00e93d63 780$msgcode['delIPv4Prefix']['OK'] = 49;
b6a7d936 781$msgcode['delIPv4Prefix']['ERR'] = 100;
42023f03 782function delIPv4Prefix ()
e673ee24 783{
0cc24e9a 784 assertUIntArg ('id');
42023f03 785 $error = destroyIPv4Prefix ($_REQUEST['id']);
e673ee24 786 if ($error != '')
135080d8 787 return buildRedirectURL (__FUNCTION__, 'ERR', array ($error));
e673ee24 788 else
135080d8 789 return buildRedirectURL (__FUNCTION__, 'OK');
e673ee24
DO
790}
791
00e93d63 792$msgcode['delIPv6Prefix']['OK'] = 49;
21ee3351
AA
793$msgcode['delIPv6Prefix']['ERR'] = 100;
794function delIPv6Prefix ()
795{
796 assertUIntArg ('id');
797 $error = destroyIPv6Prefix ($_REQUEST['id']);
798 if ($error != '')
799 return buildRedirectURL (__FUNCTION__, 'ERR', array ($error));
800 else
801 return buildRedirectURL (__FUNCTION__, 'OK');
802}
803
00e93d63 804$msgcode['editAddress']['OK'] = 51;
b6a7d936 805$msgcode['editAddress']['ERR'] = 100;
e673ee24
DO
806function editAddress ()
807{
0cc24e9a 808 assertStringArg ('name', TRUE);
e673ee24 809
e673ee24
DO
810 if (isset ($_REQUEST['reserved']))
811 $reserved = $_REQUEST['reserved'];
812 else
813 $reserved = 'off';
da958e52 814 $error = updateAddress ($_REQUEST['ip'], $_REQUEST['name'], $reserved == 'on' ? 'yes' : 'no');
e673ee24 815 if ($error != '')
135080d8 816 return buildRedirectURL (__FUNCTION__, 'ERR', array ($error));
e673ee24 817 else
135080d8 818 return buildRedirectURL (__FUNCTION__, 'OK');
e673ee24
DO
819}
820
00e93d63 821$msgcode['editv6Address']['OK'] = 51;
21ee3351
AA
822$msgcode['editv6Address']['ERR'] = 100;
823function editv6Address ()
824{
825 $ipv6 = assertIPArg ('ip');
826 assertStringArg ('name', TRUE);
827
828 if (isset ($_REQUEST['reserved']))
829 $reserved = $_REQUEST['reserved'];
830 else
831 $reserved = 'off';
832 $error = updateAddress ($ipv6, $_REQUEST['name'], $reserved == 'on' ? 'yes' : 'no');
833 if ($error != '')
834 return buildRedirectURL (__FUNCTION__, 'ERR', array ($error));
835 else
836 return buildRedirectURL (__FUNCTION__, 'OK');
837}
838
00e93d63 839$msgcode['createUser']['OK'] = 5;
b6a7d936 840$msgcode['createUser']['ERR'] = 102;
cced6b7d 841function createUser ()
e673ee24 842{
0cc24e9a
DY
843 assertStringArg ('username');
844 assertStringArg ('realname', TRUE);
845 assertStringArg ('password');
e673ee24 846 $username = $_REQUEST['username'];
93bdb7ba 847 $password = sha1 ($_REQUEST['password']);
e673ee24 848 $result = commitCreateUserAccount ($username, $_REQUEST['realname'], $password);
f857f71f 849 if ($result != TRUE)
135080d8 850 return buildRedirectURL (__FUNCTION__, 'ERR', array ($username));
f857f71f
DO
851 if (isset ($_REQUEST['taglist']))
852 produceTagsForLastRecord ('user', $_REQUEST['taglist']);
853 return buildRedirectURL (__FUNCTION__, 'OK', array ($username));
e673ee24
DO
854}
855
00e93d63
DO
856$msgcode['updateUser']['OK'] = 7;
857$msgcode['updateUser']['ERR2'] = 104;
cced6b7d 858function updateUser ()
e673ee24 859{
0cc24e9a
DY
860 assertStringArg ('username');
861 assertStringArg ('realname', TRUE);
862 assertStringArg ('password');
e673ee24
DO
863 $username = $_REQUEST['username'];
864 $new_password = $_REQUEST['password'];
a9ec91cf 865 $userinfo = spotEntity ('user', $_REQUEST['user_id']);
e673ee24 866 // Update user password only if provided password is not the same as current password hash.
b82cce3f 867 if ($new_password != $userinfo['user_password_hash'])
93bdb7ba 868 $new_password = sha1 ($new_password);
103b1e1e 869 $result = commitUpdateUserAccount ($_REQUEST['user_id'], $username, $_REQUEST['realname'], $new_password);
32832c0e 870 if ($result !== FALSE)
135080d8 871 return buildRedirectURL (__FUNCTION__, 'OK', array ($username));
e673ee24 872 else
135080d8 873 return buildRedirectURL (__FUNCTION__, 'ERR2', array ($username));
e673ee24
DO
874}
875
b6a7d936
DO
876$msgcode['updateDictionary']['OK'] = 51;
877$msgcode['updateDictionary']['ERR'] = 109;
e673ee24
DO
878function updateDictionary ()
879{
0cc24e9a
DY
880 assertUIntArg ('dict_key');
881 assertStringArg ('dict_value');
32832c0e 882 if (FALSE !== commitUpdateDictionary ($_REQUEST['chapter_no'], $_REQUEST['dict_key'], $_REQUEST['dict_value']))
135080d8 883 return buildRedirectURL (__FUNCTION__, 'OK');
e673ee24 884 else
135080d8 885 return buildRedirectURL (__FUNCTION__, 'ERR');
e673ee24
DO
886}
887
00e93d63
DO
888$msgcode['updateChapter']['OK'] = 51;
889$msgcode['updateChapter']['ERR'] = 109;
e673ee24
DO
890function updateChapter ()
891{
0cc24e9a
DY
892 assertUIntArg ('chapter_no');
893 assertStringArg ('chapter_name');
32832c0e 894 if (FALSE !== commitUpdateChapter ($_REQUEST['chapter_no'], $_REQUEST['chapter_name']))
135080d8 895 return buildRedirectURL (__FUNCTION__, 'OK');
e673ee24 896 else
135080d8 897 return buildRedirectURL (__FUNCTION__, 'ERR');
e673ee24
DO
898}
899
00e93d63
DO
900$msgcode['delChapter']['OK'] = 49;
901$msgcode['delChapter']['ERR'] = 111;
e673ee24
DO
902function delChapter ()
903{
0cc24e9a 904 assertUIntArg ('chapter_no');
e673ee24 905 if (commitDeleteChapter ($_REQUEST['chapter_no']))
135080d8 906 return buildRedirectURL (__FUNCTION__, 'OK');
e673ee24 907 else
135080d8 908 return buildRedirectURL (__FUNCTION__, 'ERR');
e673ee24
DO
909}
910
00e93d63
DO
911$msgcode['changeAttribute']['OK'] = 51;
912$msgcode['changeAttribute']['ERR'] = 109;
e673ee24
DO
913function changeAttribute ()
914{
0cc24e9a
DY
915 assertUIntArg ('attr_id');
916 assertStringArg ('attr_name');
32832c0e 917 if (FALSE !== commitUpdateAttribute ($_REQUEST['attr_id'], $_REQUEST['attr_name']))
135080d8 918 return buildRedirectURL (__FUNCTION__, 'OK');
e673ee24 919 else
135080d8 920 return buildRedirectURL (__FUNCTION__, 'ERR');
e673ee24
DO
921}
922
b6a7d936 923$msgcode['supplementAttrMap']['OK'] = 48;
7028a42c 924$msgcode['supplementAttrMap']['ERR1'] = 154;
00e93d63 925$msgcode['supplementAttrMap']['ERR2'] = 110;
e673ee24
DO
926function supplementAttrMap ()
927{
0cc24e9a
DY
928 assertUIntArg ('attr_id');
929 assertUIntArg ('objtype_id');
7028a42c
DO
930 $attrMap = getAttrMap();
931 if ($attrMap[$_REQUEST['attr_id']]['type'] != 'dict')
d5add09a 932 $chapter_id = NULL;
7028a42c
DO
933 else
934 {
d5add09a
DO
935 try
936 {
937 assertUIntArg ('chapter_no');
938 }
939 catch (InvalidRequestArgException $e)
940 {
7028a42c 941 return buildRedirectURL (__FUNCTION__, 'ERR1', array ('chapter not selected'));
d5add09a
DO
942 }
943 $chapter_id = $_REQUEST['chapter_no'];
7028a42c 944 }
654e4636 945 if (commitSupplementAttrMap ($_REQUEST['attr_id'], $_REQUEST['objtype_id'], $chapter_id) !== FALSE)
135080d8 946 return buildRedirectURL (__FUNCTION__, 'OK');
e673ee24 947 else
7028a42c 948 return buildRedirectURL (__FUNCTION__, 'ERR2');
e673ee24
DO
949}
950
00e93d63 951$msgcode['clearSticker']['OK'] = 49;
b6a7d936 952$msgcode['clearSticker']['ERR'] = 120;
22bb04da 953function clearSticker ()
e673ee24 954{
0cc24e9a 955 assertUIntArg ('attr_id');
654e4636 956 if (commitResetAttrValue ($_REQUEST['object_id'], $_REQUEST['attr_id']) !== FALSE)
135080d8 957 return buildRedirectURL (__FUNCTION__, 'OK');
e673ee24 958 else
135080d8 959 return buildRedirectURL (__FUNCTION__, 'ERR');
e673ee24
DO
960}
961
e97e8866 962$msgcode['updateObjectAllocation']['OK'] = 63;
4fbb5a00
DY
963function updateObjectAllocation ()
964{
e97e8866
DO
965 if (!isset ($_REQUEST['got_atoms']))
966 {
967 unset($_GET['page']);
968 unset($_GET['tab']);
969 unset($_GET['op']);
970 unset($_POST['page']);
971 unset($_POST['tab']);
972 unset($_POST['op']);
973 return buildWideRedirectURL (array(), NULL, NULL, array_merge ($_GET, $_POST));
974 }
975 $object_id = $_REQUEST['object_id'];
976 $workingRacksData = array();
977 foreach ($_REQUEST['rackmulti'] as $cand_id)
4fbb5a00 978 {
e97e8866 979 if (!isset ($workingRacksData[$cand_id]))
4fbb5a00 980 {
e97e8866 981 $rackData = spotEntity ('rack', $cand_id);
e97e8866
DO
982 amplifyCell ($rackData);
983 $workingRacksData[$cand_id] = $rackData;
4fbb5a00 984 }
e97e8866 985 }
2135fd83 986
e97e8866
DO
987 foreach ($workingRacksData as &$rd)
988 applyObjectMountMask ($rd, $object_id);
4fbb5a00 989
e97e8866
DO
990 $oldMolecule = getMoleculeForObject ($object_id);
991 $changecnt = 0;
992 $log = array();
993 foreach ($workingRacksData as $rack_id => $rackData)
4fbb5a00 994 {
e97e8866
DO
995 $logrecord = processGridForm ($rackData, 'F', 'T', $object_id);
996 $log[] = $logrecord;
997 if ($logrecord['code'] == 300)
998 continue;
999 $changecnt++;
1000 // Reload our working copy after form processing.
1001 $rackData = spotEntity ('rack', $cand_id);
1002 amplifyCell ($rackData);
1003 applyObjectMountMask ($rackData, $object_id);
1004 $workingRacksData[$rack_id] = $rackData;
4fbb5a00 1005 }
e97e8866
DO
1006 if (!$changecnt)
1007 return buildRedirectURL (__FUNCTION__, 'OK', $changecnt);
1008 // Log a record.
1009 $newMolecule = getMoleculeForObject ($object_id);
1010 $oc = count ($oldMolecule);
1011 $nc = count ($newMolecule);
1012 $omid = $oc ? createMolecule ($oldMolecule) : 'NULL';
1013 $nmid = $nc ? createMolecule ($newMolecule) : 'NULL';
1014 global $remote_username;
1015 $comment = empty ($_REQUEST['comment']) ? 'NULL' : "'${_REQUEST['comment']}'";
1016 $query =
1017 "insert into MountOperation(object_id, old_molecule_id, new_molecule_id, user_name, comment) " .
1018 "values (${object_id}, ${omid}, ${nmid}, '${remote_username}', ${comment})";
1019 global $dbxlink;
1020 $result = $dbxlink->query ($query);
1021 if ($result == NULL)
1022 $log[] = array ('code' => 500, 'message' => 'SQL query failed during history logging.');
1023 else
1024 $log[] = array ('code' => 200, 'message' => 'History logged.');
1025 return buildWideRedirectURL ($log);
4fbb5a00
DY
1026}
1027
00e93d63
DO
1028$msgcode['updateObject']['OK'] = 51;
1029$msgcode['updateObject']['ERR'] = 109;
22bb04da
DO
1030function updateObject ()
1031{
0cc24e9a 1032 assertUIntArg ('num_attrs', TRUE);
0cc24e9a
DY
1033 assertStringArg ('object_name', TRUE);
1034 assertStringArg ('object_label', TRUE);
1035 assertStringArg ('object_barcode', TRUE);
1036 assertStringArg ('object_asset_no', TRUE);
22bb04da
DO
1037 if (isset ($_REQUEST['object_has_problems']) and $_REQUEST['object_has_problems'] == 'on')
1038 $has_problems = 'yes';
1039 else
1040 $has_problems = 'no';
1041
1042 if (commitUpdateObject (
1043 $_REQUEST['object_id'],
1044 $_REQUEST['object_name'],
1045 $_REQUEST['object_label'],
1046 $_REQUEST['object_barcode'],
22bb04da
DO
1047 $has_problems,
1048 $_REQUEST['object_asset_no'],
1049 $_REQUEST['object_comment']
1050 ) !== TRUE)
135080d8 1051 return buildRedirectURL (__FUNCTION__, 'ERR');
22bb04da 1052
cdd3efe9 1053 // Update optional attributes
f59e8cf5 1054 $oldvalues = getAttrValues ($_REQUEST['object_id']);
0dfb8a2a 1055 $result = array();
0f63538a
DO
1056 $num_attrs = isset ($_REQUEST['num_attrs']) ? $_REQUEST['num_attrs'] : 0;
1057 for ($i = 0; $i < $num_attrs; $i++)
0dfb8a2a 1058 {
0cc24e9a 1059 assertUIntArg ("${i}_attr_id");
0dfb8a2a
DO
1060 $attr_id = $_REQUEST["${i}_attr_id"];
1061
01d82bd2
RF
1062 // Field is empty, delete attribute and move on. OR if the field type is a dictionary and it is the --NOT SET-- value of 0
1063 if (!strlen ($_REQUEST["${i}_value"]) || ($oldvalues[$attr_id]['type']=='dict' && $_REQUEST["${i}_value"] == 0))
0dfb8a2a 1064 {
103b1e1e 1065 commitResetAttrValue ($_REQUEST['object_id'], $attr_id);
0dfb8a2a
DO
1066 continue;
1067 }
1068
1069 // The value could be uint/float, but we don't know ATM. Let SQL
1070 // server check this and complain.
0cc24e9a 1071 assertStringArg ("${i}_value");
0dfb8a2a
DO
1072 $value = $_REQUEST["${i}_value"];
1073 switch ($oldvalues[$attr_id]['type'])
1074 {
1075 case 'uint':
1076 case 'float':
1077 case 'string':
1078 $oldvalue = $oldvalues[$attr_id]['value'];
1079 break;
1080 case 'dict':
1081 $oldvalue = $oldvalues[$attr_id]['key'];
1082 break;
1083 default:
0dfb8a2a 1084 }
59a83bd8 1085 if ($value === $oldvalue) // ('' == 0), but ('' !== 0)
0dfb8a2a
DO
1086 continue;
1087
1088 // Note if the queries succeed or not, it determines which page they see.
103b1e1e 1089 $result[] = commitUpdateAttrValue ($_REQUEST['object_id'], $attr_id, $value);
0dfb8a2a 1090 }
103b1e1e 1091 if (in_array (FALSE, $result))
135080d8 1092 return buildRedirectURL (__FUNCTION__, 'ERR');
0dfb8a2a 1093
cdd3efe9
AD
1094 // Invalidate thumb cache of all racks objects could occupy.
1095 foreach (getResidentRacksData ($_REQUEST['object_id'], FALSE) as $rack_id)
1096 resetThumbCache ($rack_id);
1097
135080d8 1098 return buildRedirectURL (__FUNCTION__, 'OK');
e673ee24
DO
1099}
1100
42d73cbf
DY
1101function addMultipleObjects()
1102{
7abce0b7 1103 $log = emptyLog();
42d73cbf 1104 $taglist = isset ($_REQUEST['taglist']) ? $_REQUEST['taglist'] : array();
42d73cbf
DY
1105 $max = getConfigVar ('MASSCOUNT');
1106 for ($i = 0; $i < $max; $i++)
1107 {
1108 if (!isset ($_REQUEST["${i}_object_type_id"]))
1109 {
57777e4a 1110 $log = mergeLogs ($log, oneLiner (184, array ($i + 1)));
42d73cbf
DY
1111 break;
1112 }
0cc24e9a
DY
1113 assertUIntArg ("${i}_object_type_id", TRUE);
1114 assertStringArg ("${i}_object_name", TRUE);
1115 assertStringArg ("${i}_object_label", TRUE);
1116 assertStringArg ("${i}_object_asset_no", TRUE);
1117 assertStringArg ("${i}_object_barcode", TRUE);
7abce0b7 1118 $name = $_REQUEST["${i}_object_name"];
42d73cbf
DY
1119
1120 // It's better to skip silently, than to print a notice.
7abce0b7 1121 if ($_REQUEST["${i}_object_type_id"] == 0)
42d73cbf 1122 continue;
fee7977b 1123 if (($object_id = commitAddObject
7abce0b7
DO
1124 (
1125 $name,
1126 $_REQUEST["${i}_object_label"],
1127 $_REQUEST["${i}_object_barcode"],
1128 $_REQUEST["${i}_object_type_id"],
1129 $_REQUEST["${i}_object_asset_no"],
1130 $taglist
fee7977b
DO
1131 )) !== FALSE){
1132 $info = spotEntity ('object', $object_id);
1133 // FIXME: employ amplifyCell() instead of calling loader functions directly
1134 amplifyCell ($info);
00e93d63 1135 $log = mergeLogs ($log, oneLiner (5, array ('<a href="' . makeHref (array ('page' => 'object', 'tab' => 'default', 'object_id' => $object_id)) . '">' . $info['dname'] . '</a>')));
fee7977b 1136 }else{
00e93d63 1137 $log = mergeLogs ($log, oneLiner (147, array ($name)));
fee7977b 1138 }
42d73cbf 1139 }
7abce0b7 1140 return buildWideRedirectURL ($log);
42d73cbf
DY
1141}
1142
1143function addLotOfObjects()
1144{
7abce0b7 1145 $log = emptyLog();
42d73cbf 1146 $taglist = isset ($_REQUEST['taglist']) ? $_REQUEST['taglist'] : array();
0cc24e9a
DY
1147 assertUIntArg ('global_type_id', TRUE);
1148 assertStringArg ('namelist', TRUE);
42d73cbf 1149 $global_type_id = $_REQUEST['global_type_id'];
59a83bd8 1150 if ($global_type_id == 0 or !strlen ($_REQUEST['namelist']))
57777e4a 1151 $log = mergeLogs ($log, oneLiner (186));
42d73cbf
DY
1152 else
1153 {
1154 // The name extractor below was stolen from ophandlers.php:addMultiPorts()
7f42d792 1155 $names1 = explode ("\n", $_REQUEST['namelist']);
42d73cbf
DY
1156 $names2 = array();
1157 foreach ($names1 as $line)
1158 {
1159 $parts = explode ('\r', $line);
1160 reset ($parts);
59a83bd8 1161 if (!strlen ($parts[0]))
42d73cbf
DY
1162 continue;
1163 else
1164 $names2[] = rtrim ($parts[0]);
1165 }
57777e4a 1166 foreach ($names2 as $name)
9d535a0c
DO
1167 if (($object_id = commitAddObject ($name, '', '', $global_type_id, '', $taglist)) !== FALSE)
1168 {
1169 $info = spotEntity ('object', $object_id);
1170 amplifyCell ($info);
00e93d63 1171 $log = mergeLogs ($log, oneLiner (5, array ('<a href="' . makeHref (array ('page' => 'object', 'tab' => 'default', 'object_id' => $object_id)) . '">' . $info['dname'] . '</a>')));
9d535a0c 1172 }
42d73cbf 1173 else
00e93d63 1174 $log = mergeLogs ($log, oneLiner (147, array ($name)));
42d73cbf 1175 }
7abce0b7 1176 return buildWideRedirectURL ($log);
42d73cbf
DY
1177}
1178
00e93d63 1179$msgcode['deleteObject']['OK'] = 6;
52b34485
AD
1180function deleteObject ()
1181{
0cc24e9a 1182 assertUIntArg ('object_id');
4bb5b87f 1183 $oinfo = spotEntity ('object', $_REQUEST['object_id']);
c78a40ec 1184
f0e2c99f 1185 $racklist = getResidentRacksData ($_REQUEST['object_id'], FALSE);
4bb5b87f 1186 commitDeleteObject ($_REQUEST['object_id']);
f0e2c99f
DO
1187 foreach ($racklist as $rack_id)
1188 resetThumbCache ($rack_id);
abd1e9ac
DO
1189 return buildRedirectURL (__FUNCTION__, 'OK', array ($oinfo['dname']));
1190}
52b34485 1191
00e93d63 1192$msgcode['resetObject']['OK'] = 57;
abd1e9ac
DO
1193function resetObject ()
1194{
abd1e9ac
DO
1195 $oinfo = spotEntity ('object', $_REQUEST['object_id']);
1196
1197 $racklist = getResidentRacksData ($_REQUEST['object_id'], FALSE);
1198 commitResetObject ($_REQUEST['object_id']);
1199 foreach ($racklist as $rack_id)
1200 resetThumbCache ($rack_id);
00e93d63 1201 return buildRedirectURL (__FUNCTION__, 'OK');
52b34485
AD
1202}
1203
00e93d63
DO
1204$msgcode['useupPort']['OK'] = 49;
1205$msgcode['useupPort']['ERR'] = 111;
e673ee24
DO
1206function useupPort ()
1207{
0cc24e9a 1208 assertUIntArg ('port_id');
32832c0e 1209 if (FALSE !== commitUseupPort ($_REQUEST['port_id']))
135080d8 1210 return buildRedirectURL (__FUNCTION__, 'OK');
e673ee24 1211 else
135080d8 1212 return buildRedirectURL (__FUNCTION__, 'ERR');
e673ee24
DO
1213}
1214
00e93d63 1215$msgcode['updateUI']['OK'] = 51;
4fe32e78
DY
1216function updateUI ()
1217{
0cc24e9a 1218 assertUIntArg ('num_vars');
4fe32e78 1219
103b1e1e 1220 for ($i = 0; $i < $_REQUEST['num_vars']; $i++)
4fe32e78 1221 {
0cc24e9a
DY
1222 assertStringArg ("${i}_varname");
1223 assertStringArg ("${i}_varvalue", TRUE);
4fe32e78 1224 $varname = $_REQUEST["${i}_varname"];
4fe32e78 1225 $varvalue = $_REQUEST["${i}_varvalue"];
4fe32e78 1226
c461c579 1227 // If form value = value in DB, don't bother updating DB
ed941e67 1228 if (!isConfigVarChanged($varname, $varvalue))
4fe32e78 1229 continue;
3a089a44
DO
1230 // any exceptions will be handled by process.php
1231 setConfigVar ($varname, $varvalue, TRUE);
3540d15c
DY
1232 }
1233 return buildRedirectURL (__FUNCTION__, 'OK');
1234}
1235
1236$msgcode['saveMyPreferences']['OK'] = 56;
3540d15c
DY
1237function saveMyPreferences ()
1238{
1239 assertUIntArg ('num_vars');
1240
1241 for ($i = 0; $i < $_REQUEST['num_vars']; $i++)
1242 {
1243 assertStringArg ("${i}_varname");
1244 assertStringArg ("${i}_varvalue", TRUE);
1245 $varname = $_REQUEST["${i}_varname"];
1246 $varvalue = $_REQUEST["${i}_varvalue"];
1247
1248 // If form value = value in DB, don't bother updating DB
ed941e67 1249 if (!isConfigVarChanged($varname, $varvalue))
3540d15c 1250 continue;
3a089a44 1251 setUserConfigVar ($varname, $varvalue);
3540d15c
DY
1252 }
1253 return buildRedirectURL (__FUNCTION__, 'OK');
1254}
1255
1256$msgcode['resetMyPreference']['OK'] = 56;
3540d15c
DY
1257function resetMyPreference ()
1258{
1259 assertStringArg ("varname");
3a089a44 1260 resetUserConfigVar ($_REQUEST["varname"]);
135080d8 1261 return buildRedirectURL (__FUNCTION__, 'OK');
4fe32e78
DY
1262}
1263
b6a7d936 1264$msgcode['resetUIConfig']['OK'] = 57;
b07f617c
DO
1265function resetUIConfig()
1266{
b07f617c
DO
1267 setConfigVar ('MASSCOUNT','15');
1268 setConfigVar ('MAXSELSIZE','30');
b07f617c
DO
1269 setConfigVar ('ROW_SCALE','2');
1270 setConfigVar ('PORTS_PER_ROW','12');
1271 setConfigVar ('IPV4_ADDRS_PER_PAGE','256');
1272 setConfigVar ('DEFAULT_RACK_HEIGHT','42');
b5ce46aa
DO
1273 setConfigVar ('DEFAULT_SLB_VS_PORT','');
1274 setConfigVar ('DEFAULT_SLB_RS_PORT','');
72281138 1275 setConfigVar ('DETECT_URLS','no');
4b8d413e 1276 setConfigVar ('RACK_PRESELECT_THRESHOLD','1');
b108de49 1277 setConfigVar ('DEFAULT_IPV4_RS_INSERVICE','no');
8dfb997c 1278 setConfigVar ('AUTOPORTS_CONFIG','4 = 1*33*kvm + 2*24*eth%u;15 = 1*446*kvm');
194e3748
DO
1279 setConfigVar ('SHOW_EXPLICIT_TAGS','yes');
1280 setConfigVar ('SHOW_IMPLICIT_TAGS','yes');
1281 setConfigVar ('SHOW_AUTOMATIC_TAGS','no');
a477e405 1282 setConfigVar ('DEFAULT_OBJECT_TYPE','4');
2754cefc 1283 setConfigVar ('IPV4_AUTO_RELEASE','1');
a53dc9df 1284 setConfigVar ('SHOW_LAST_TAB', 'no');
f0ed1181 1285 setConfigVar ('EXT_IPV4_VIEW', 'yes');
efee2692 1286 setConfigVar ('TREE_THRESHOLD', '25');
2be3fd23 1287 setConfigVar ('IPV4_JAYWALK', 'no');
9318d2ef 1288 setConfigVar ('ADDNEW_AT_TOP', 'yes');
64347dcf 1289 setConfigVar ('IPV4_TREE_SHOW_USAGE', 'yes');
37e59768
DO
1290 setConfigVar ('PREVIEW_TEXT_MAXCHARS', '10240');
1291 setConfigVar ('PREVIEW_TEXT_ROWS', '25');
1292 setConfigVar ('PREVIEW_TEXT_COLS', '80');
1293 setConfigVar ('PREVIEW_IMAGE_MAXPXS', '320');
f3d274bf 1294 setConfigVar ('VENDOR_SIEVE', '');
35bf153d 1295 setConfigVar ('IPV4LB_LISTSRC', '{$typeid_4}');
8fee82b4
DO
1296 setConfigVar ('IPV4OBJ_LISTSRC','{$typeid_4} or {$typeid_7} or {$typeid_8} or {$typeid_12} or {$typeid_445} or {$typeid_447} or {$typeid_798}');
1297 setConfigVar ('IPV4NAT_LISTSRC','{$typeid_4} or {$typeid_7} or {$typeid_8} or {$typeid_798}');
35bf153d
DO
1298 setConfigVar ('ASSETWARN_LISTSRC','{$typeid_4} or {$typeid_7} or {$typeid_8}');
1299 setConfigVar ('NAMEWARN_LISTSRC','{$typeid_4} or {$typeid_7} or {$typeid_8}');
f5883ec1 1300 setConfigVar ('RACKS_PER_ROW','12');
590e1281 1301 setConfigVar ('FILTER_PREDICATE_SIEVE','');
23cdc7e9
DO
1302 setConfigVar ('FILTER_DEFAULT_ANDOR','or');
1303 setConfigVar ('FILTER_SUGGEST_ANDOR','yes');
1304 setConfigVar ('FILTER_SUGGEST_TAGS','yes');
1305 setConfigVar ('FILTER_SUGGEST_PREDICATES','yes');
1306 setConfigVar ('FILTER_SUGGEST_EXTRA','no');
8fee82b4 1307 setConfigVar ('DEFAULT_SNMP_COMMUNITY','public');
f06fe423 1308 setConfigVar ('IPV4_ENABLE_KNIGHT','yes');
9e51318b
DO
1309 setConfigVar ('TAGS_TOPLIST_SIZE','50');
1310 setConfigVar ('TAGS_QUICKLIST_SIZE','20');
1311 setConfigVar ('TAGS_QUICKLIST_THRESHOLD','50');
f44fdef9 1312 setConfigVar ('ENABLE_MULTIPORT_FORM', 'no');
2400d7ec
DO
1313 setConfigVar ('DEFAULT_PORT_IIF_ID', '1');
1314 setConfigVar ('DEFAULT_PORT_OIF_IDS', '1=24; 3=1078; 4=1077; 5=1079; 6=1080; 8=1082; 9=1084');
4a47d34b 1315 setConfigVar ('IPV4_TREE_RTR_AS_CELL', 'yes');
cd3775e9 1316 setConfigVar ('PROXIMITY_RANGE', 0);
ca4eb604 1317 setConfigVar ('IPV4_TREE_SHOW_VLAN', 'yes');
407ed7bb
DO
1318 setConfigVar ('VLANSWITCH_LISTSRC', '');
1319 setConfigVar ('VLANIPV4NET_LISTSRC', '');
2fb1f79b
DO
1320 setConfigVar ('DEFAULT_VDOM_ID', '');
1321 setConfigVar ('DEFAULT_VST_ID', '');
01b9a31a 1322 setConfigVar ('STATIC_FILTER', 'yes');
37cb9e18
DO
1323 setConfigVar ('8021Q_DEPLOY_MINAGE', '300');
1324 setConfigVar ('8021Q_DEPLOY_MAXAGE', '3600');
1325 setConfigVar ('8021Q_DEPLOY_RETRY', '10800');
2582446d 1326 setConfigVar ('8021Q_WRI_AFTER_CONFT_LISTSRC', 'false');
4492050b 1327 setConfigVar ('8021Q_INSTANT_DEPLOY', 'no');
b49a479e
DO
1328 setConfigVar ('CDP_RUNNERS_LISTSRC', '');
1329 setConfigVar ('LLDP_RUNNERS_LISTSRC', '');
0328f6d6 1330 setConfigVar ('HNDP_RUNNERS_LISTSRC', '');
95857b5c 1331 setConfigVar ('SHRINK_TAG_TREE_ON_CLICK', 'yes');
1ebbf889 1332 setConfigVar ('MAX_UNFILTERED_ENTITIES', '0');
61e79d63 1333 setConfigVar ('SYNCDOMAIN_MAX_PROCESSES', '0');
135080d8 1334 return buildRedirectURL (__FUNCTION__, 'OK');
b07f617c
DO
1335}
1336
00e93d63
DO
1337$msgcode['addRealServer']['OK'] = 48;
1338$msgcode['addRealServer']['ERR'] = 110;
732e4578 1339// Add single record.
ca461127
DO
1340function addRealServer ()
1341{
0cc24e9a
DY
1342 assertUIntArg ('pool_id');
1343 assertIPv4Arg ('remoteip');
1344 assertStringArg ('rsport', TRUE);
1345 assertStringArg ('rsconfig', TRUE);
103b1e1e
DO
1346 if (!addRStoRSPool (
1347 $_REQUEST['pool_id'],
1348 $_REQUEST['remoteip'],
1349 $_REQUEST['rsport'],
1350 getConfigVar ('DEFAULT_IPV4_RS_INSERVICE'),
1351 $_REQUEST['rsconfig']
1352 ))
135080d8 1353 return buildRedirectURL (__FUNCTION__, 'ERR');
d6517a21 1354 else
135080d8 1355 return buildRedirectURL (__FUNCTION__, 'OK');
d6517a21
DO
1356}
1357
b6a7d936
DO
1358$msgcode['addRealServers']['OK'] = 37;
1359$msgcode['addRealServers']['ERR1'] = 131;
1360$msgcode['addRealServers']['ERR2'] = 127;
732e4578
DO
1361// Parse textarea submitted and try adding a real server for each line.
1362function addRealServers ()
1363{
0cc24e9a
DY
1364 assertStringArg ('format');
1365 assertStringArg ('rawtext');
732e4578
DO
1366 $ngood = $nbad = 0;
1367 $rsconfig = '';
1368 // Keep in mind, that the text will have HTML entities (namely '>') escaped.
7f42d792 1369 foreach (explode ("\n", dos2unix ($_REQUEST['rawtext'])) as $line)
732e4578 1370 {
59a83bd8 1371 if (!strlen ($line))
732e4578
DO
1372 continue;
1373 $match = array ();
1374 switch ($_REQUEST['format'])
1375 {
1376 case 'ipvs_2': // address and port only
1377 if (!preg_match ('/^ -&gt; ([0-9\.]+):([0-9]+) /', $line, $match))
1378 continue;
103b1e1e 1379 if (addRStoRSPool ($_REQUEST['pool_id'], $match[1], $match[2], getConfigVar ('DEFAULT_IPV4_RS_INSERVICE'), ''))
732e4578
DO
1380 $ngood++;
1381 else
1382 $nbad++;
1383 break;
1384 case 'ipvs_3': // address, port and weight
1385 if (!preg_match ('/^ -&gt; ([0-9\.]+):([0-9]+) +[a-zA-Z]+ +([0-9]+) /', $line, $match))
1386 continue;
103b1e1e 1387 if (addRStoRSPool ($_REQUEST['pool_id'], $match[1], $match[2], getConfigVar ('DEFAULT_IPV4_RS_INSERVICE'), 'weight ' . $match[3]))
732e4578
DO
1388 $ngood++;
1389 else
1390 $nbad++;
1391 break;
e69c2aa3
DO
1392 case 'ssv_2': // IP address and port
1393 if (!preg_match ('/^([0-9\.]+) ([0-9]+)$/', $line, $match))
1394 continue;
103b1e1e 1395 if (addRStoRSPool ($_REQUEST['pool_id'], $match[1], $match[2], getConfigVar ('DEFAULT_IPV4_RS_INSERVICE'), ''))
e69c2aa3
DO
1396 $ngood++;
1397 else
1398 $nbad++;
1399 break;
948c37e3
DO
1400 case 'ssv_1': // IP address
1401 if (!preg_match ('/^([0-9\.]+)$/', $line, $match))
1402 continue;
1403 if (addRStoRSPool ($_REQUEST['pool_id'], $match[1], 0, getConfigVar ('DEFAULT_IPV4_RS_INSERVICE'), ''))
1404 $ngood++;
1405 else
1406 $nbad++;
1407 break;
732e4578 1408 default:
135080d8 1409 return buildRedirectURL (__FUNCTION__, 'ERR1');
732e4578
DO
1410 break;
1411 }
1412 }
1413 if ($nbad == 0 and $ngood > 0)
135080d8 1414 return buildRedirectURL (__FUNCTION__, 'OK', array ($ngood));
732e4578 1415 else
135080d8 1416 return buildRedirectURL (__FUNCTION__, 'ERR2', array ($ngood, $nbad));
732e4578
DO
1417}
1418
00e93d63 1419$msgcode['addVService']['OK'] = 48;
d6517a21
DO
1420function addVService ()
1421{
0cc24e9a
DY
1422 assertIPv4Arg ('vip');
1423 assertUIntArg ('vport');
a9ec91cf 1424 genericAssertion ('proto', 'enum/ipproto');
0cc24e9a
DY
1425 assertStringArg ('name', TRUE);
1426 assertStringArg ('vsconfig', TRUE);
1427 assertStringArg ('rsconfig', TRUE);
a9ec91cf 1428 usePreparedExecuteBlade
c63a8d6e 1429 (
a9ec91cf
DO
1430 'INSERT INTO IPv4VS (vip, vport, proto, name, vsconfig, rsconfig) VALUES (INET_ATON(?), ?, ?, ?, ?, ?)',
1431 array
1432 (
1433 $_REQUEST['vip'],
1434 $_REQUEST['vport'],
1435 $_REQUEST['proto'],
1436 !mb_strlen ($_REQUEST['name']) ? NULL : $_REQUEST['name'],
1437 !strlen ($_REQUEST['vsconfig']) ? NULL : $_REQUEST['vsconfig'],
1438 !strlen ($_REQUEST['rsconfig']) ? NULL : $_REQUEST['rsconfig'],
1439 )
c63a8d6e 1440 );
a9ec91cf
DO
1441 produceTagsForLastRecord ('ipv4vs', isset ($_REQUEST['taglist']) ? $_REQUEST['taglist'] : array());
1442 return buildRedirectURL (__FUNCTION__, 'OK');
fb1c4a54
DO
1443}
1444
00e93d63
DO
1445$msgcode['deleteVService']['OK'] = 49;
1446$msgcode['deleteVService']['ERR'] = 111;
d6517a21
DO
1447function deleteVService ()
1448{
0cc24e9a 1449 assertUIntArg ('vs_id');
e02e1941 1450 if (!commitDeleteVS ($_REQUEST['vs_id']))
135080d8 1451 return buildRedirectURL (__FUNCTION__, 'ERR');
3241551e 1452 else
135080d8 1453 return buildRedirectURL (__FUNCTION__, 'OK');
3241551e
DO
1454}
1455
1f54e1ba
DO
1456$msgcode['updateSLBDefConfig']['OK'] = 43;
1457$msgcode['updateSLBDefConfig']['ERR'] = 109;
1458function updateSLBDefConfig ()
1459{
1460 $data = array(
1461 'vs' => $_REQUEST['vsconfig'],
1462 'rs' => $_REQUEST['rsconfig']
1463 );
1464 if (!commitUpdateSLBDefConf ($data))
1465 return buildRedirectURL (__FUNCTION__, 'ERR');
1466 else
1467 return buildRedirectURL (__FUNCTION__, 'OK');
1468}
1469
00e93d63
DO
1470$msgcode['updateRealServer']['OK'] = 51;
1471$msgcode['updateRealServer']['ERR'] = 109;
fb1c4a54
DO
1472function updateRealServer ()
1473{
0cc24e9a
DY
1474 assertUIntArg ('rs_id');
1475 assertIPv4Arg ('rsip');
1476 assertStringArg ('rsport', TRUE);
1477 assertStringArg ('rsconfig', TRUE);
a5c589d2 1478 if (FALSE === commitUpdateRS (
103b1e1e
DO
1479 $_REQUEST['rs_id'],
1480 $_REQUEST['rsip'],
1481 $_REQUEST['rsport'],
1482 $_REQUEST['rsconfig']
1483 ))
135080d8 1484 return buildRedirectURL (__FUNCTION__, 'ERR');
fb1c4a54 1485 else
135080d8 1486 return buildRedirectURL (__FUNCTION__, 'OK');
ca461127
DO
1487}
1488
00e93d63
DO
1489$msgcode['updateLoadBalancer']['OK'] = 51;
1490$msgcode['updateLoadBalancer']['ERR'] = 109;
c1ca768c 1491function updateLoadBalancer ()
3241551e 1492{
0cc24e9a
DY
1493 assertUIntArg ('object_id');
1494 assertUIntArg ('pool_id');
1495 assertUIntArg ('vs_id');
1496 assertStringArg ('vsconfig', TRUE);
1497 assertStringArg ('rsconfig', TRUE);
1f54e1ba
DO
1498 if (! empty($_REQUEST['prio']))
1499 assertUIntArg('prio', TRUE);
1500
a5c589d2 1501 if (FALSE === commitUpdateLB (
103b1e1e
DO
1502 $_REQUEST['object_id'],
1503 $_REQUEST['pool_id'],
1504 $_REQUEST['vs_id'],
1505 $_REQUEST['vsconfig'],
1f54e1ba
DO
1506 $_REQUEST['rsconfig'],
1507 $_REQUEST['prio']
103b1e1e 1508 ))
135080d8 1509 return buildRedirectURL (__FUNCTION__, 'ERR');
d6517a21 1510 else
135080d8 1511 return buildRedirectURL (__FUNCTION__, 'OK');
d6517a21
DO
1512}
1513
00e93d63
DO
1514$msgcode['updateVService']['OK'] = 51;
1515$msgcode['updateVService']['ERR'] = 109;
d6517a21
DO
1516function updateVService ()
1517{
0cc24e9a
DY
1518 assertUIntArg ('vs_id');
1519 assertIPv4Arg ('vip');
1520 assertUIntArg ('vport');
1d84140d 1521 genericAssertion ('proto', 'enum/ipproto');
0cc24e9a
DY
1522 assertStringArg ('name', TRUE);
1523 assertStringArg ('vsconfig', TRUE);
1524 assertStringArg ('rsconfig', TRUE);
a5c589d2 1525 if (FALSE === commitUpdateVS (
103b1e1e
DO
1526 $_REQUEST['vs_id'],
1527 $_REQUEST['vip'],
1528 $_REQUEST['vport'],
1529 $_REQUEST['proto'],
1530 $_REQUEST['name'],
1531 $_REQUEST['vsconfig'],
1532 $_REQUEST['rsconfig']
1533 ))
135080d8 1534 return buildRedirectURL (__FUNCTION__, 'ERR');
3241551e 1535 else
135080d8 1536 return buildRedirectURL (__FUNCTION__, 'OK');
3241551e
DO
1537}
1538
00e93d63
DO
1539$msgcode['addLoadBalancer']['OK'] = 48;
1540$msgcode['addLoadBalancer']['ERR'] = 110;
3241551e
DO
1541function addLoadBalancer ()
1542{
0cc24e9a
DY
1543 assertUIntArg ('pool_id');
1544 assertUIntArg ('object_id');
1545 assertUIntArg ('vs_id');
1546 assertStringArg ('vsconfig', TRUE);
1547 assertStringArg ('rsconfig', TRUE);
1f54e1ba
DO
1548 if (! empty($_REQUEST['prio']))
1549 assertUIntArg('prio', TRUE);
1550
103b1e1e
DO
1551 if (!addLBtoRSPool (
1552 $_REQUEST['pool_id'],
1553 $_REQUEST['object_id'],
1554 $_REQUEST['vs_id'],
1555 $_REQUEST['vsconfig'],
1f54e1ba
DO
1556 $_REQUEST['rsconfig'],
1557 $_REQUEST['prio']
103b1e1e 1558 ))
135080d8 1559 return buildRedirectURL (__FUNCTION__, 'ERR');
3241551e 1560 else
135080d8 1561 return buildRedirectURL (__FUNCTION__, 'OK');
3241551e
DO
1562}
1563
00e93d63 1564$msgcode['addRSPool']['OK'] = 48;
b6a7d936 1565$msgcode['addRSPool']['ERR'] = 100;
5ad76f01
DO
1566function addRSPool ()
1567{
0cc24e9a
DY
1568 assertStringArg ('name', TRUE);
1569 assertStringArg ('vsconfig', TRUE);
1570 assertStringArg ('rsconfig', TRUE);
c63a8d6e
DO
1571 $error = commitCreateRSPool
1572 (
103b1e1e
DO
1573 $_REQUEST['name'],
1574 $_REQUEST['vsconfig'],
c63a8d6e
DO
1575 $_REQUEST['rsconfig'],
1576 isset ($_REQUEST['taglist']) ? $_REQUEST['taglist'] : array()
1577 );
1578 if ($error != '')
135080d8 1579 return buildRedirectURL (__FUNCTION__, 'ERR', array ($error));
5ad76f01 1580 else
135080d8 1581 return buildRedirectURL (__FUNCTION__, 'OK');
5ad76f01
DO
1582}
1583
00e93d63
DO
1584$msgcode['deleteRSPool']['OK'] = 49;
1585$msgcode['deleteRSPool']['ERR'] = 111;
5ad76f01
DO
1586function deleteRSPool ()
1587{
0cc24e9a 1588 assertUIntArg ('pool_id');
654e4636 1589 if (commitDeleteRSPool ($_REQUEST['pool_id']) === FALSE)
135080d8 1590 return buildRedirectURL (__FUNCTION__, 'ERR');
5ad76f01 1591 else
135080d8 1592 return buildRedirectURL (__FUNCTION__, 'OK');
5ad76f01
DO
1593}
1594
00e93d63
DO
1595$msgcode['updateRSPool']['OK'] = 51;
1596$msgcode['updateRSPool']['ERR'] = 109;
5ad76f01
DO
1597function updateRSPool ()
1598{
0cc24e9a
DY
1599 assertStringArg ('name', TRUE);
1600 assertStringArg ('vsconfig', TRUE);
1601 assertStringArg ('rsconfig', TRUE);
1f54e1ba
DO
1602 if (FALSE === commitUpdateRSPool
1603 (
1604 $_REQUEST['pool_id'],
1605 $_REQUEST['name'],
1606 $_REQUEST['vsconfig'],
1607 $_REQUEST['rsconfig']
1608 )
1609 )
135080d8 1610 return buildRedirectURL (__FUNCTION__, 'ERR');
5ad76f01 1611 else
135080d8 1612 return buildRedirectURL (__FUNCTION__, 'OK');
5ad76f01
DO
1613}
1614
00e93d63
DO
1615$msgcode['updateRSInService']['OK'] = 26;
1616$msgcode['updateRSInService']['ERR'] = 141;
1f7d18fa
DO
1617function updateRSInService ()
1618{
0cc24e9a 1619 assertUIntArg ('rscount');
841a7a7a 1620 $pool_id = $_REQUEST['pool_id'];
a6e91ac2
DO
1621 $orig = spotEntity ('ipv4rspool', $pool_id);
1622 amplifyCell ($orig);
1f7d18fa
DO
1623 $nbad = $ngood = 0;
1624 for ($i = 1; $i <= $_REQUEST['rscount']; $i++)
1625 {
1626 $rs_id = $_REQUEST["rsid_${i}"];
1627 if (isset ($_REQUEST["inservice_${i}"]) and $_REQUEST["inservice_${i}"] == 'on')
1628 $newval = 'yes';
1629 else
1630 $newval = 'no';
1631 if ($newval != $orig['rslist'][$rs_id]['inservice'])
1632 {
a5c589d2 1633 if (FALSE !== commitSetInService ($rs_id, $newval))
1f7d18fa
DO
1634 $ngood++;
1635 else
1636 $nbad++;
1637 }
1638 }
1639 if (!$nbad)
135080d8 1640 return buildRedirectURL (__FUNCTION__, 'OK', array ($ngood));
1f7d18fa 1641 else
135080d8 1642 return buildRedirectURL (__FUNCTION__, 'ERR', array ($nbad, $ngood));
1f7d18fa
DO
1643}
1644
b6a7d936
DO
1645$msgcode['importPTRData']['OK'] = 26;
1646$msgcode['importPTRData']['ERR'] = 141;
8d9c16e7
DO
1647// FIXME: check, that each submitted address belongs to the prefix we
1648// are operating on.
03eb5209
DO
1649function importPTRData ()
1650{
0cc24e9a 1651 assertUIntArg ('addrcount');
03eb5209 1652 $nbad = $ngood = 0;
03eb5209
DO
1653 for ($i = 0; $i < $_REQUEST['addrcount']; $i++)
1654 {
3f3bd41e 1655 $inputname = "import_${i}";
03eb5209
DO
1656 if (!isset ($_REQUEST[$inputname]) or $_REQUEST[$inputname] != 'on')
1657 continue;
0cc24e9a
DY
1658 assertIPv4Arg ("addr_${i}");
1659 assertStringArg ("descr_${i}", TRUE);
1660 assertStringArg ("rsvd_${i}");
3f3bd41e
DO
1661 // Non-existent addresses will not have this argument set in request.
1662 $rsvd = 'no';
03eb5209
DO
1663 if ($_REQUEST["rsvd_${i}"] == 'yes')
1664 $rsvd = 'yes';
3f3bd41e 1665 if (updateAddress ($_REQUEST["addr_${i}"], $_REQUEST["descr_${i}"], $rsvd) == '')
03eb5209
DO
1666 $ngood++;
1667 else
1668 $nbad++;
1669 }
1670 if (!$nbad)
135080d8 1671 return buildRedirectURL (__FUNCTION__, 'OK', array ($ngood));
03eb5209 1672 else
135080d8 1673 return buildRedirectURL (__FUNCTION__, 'ERR', array ($nbad, $ngood));
03eb5209
DO
1674}
1675
b6a7d936
DO
1676$msgcode['generateAutoPorts']['OK'] = 21;
1677$msgcode['generateAutoPorts']['ERR'] = 142;
f3f0161f
DO
1678function generateAutoPorts ()
1679{
103b1e1e 1680 global $pageno;
6297d584 1681 $info = spotEntity ('object', $_REQUEST['object_id']);
f3f0161f 1682 // Navigate away in case of success, stay at the place otherwise.
103b1e1e 1683 if (executeAutoPorts ($_REQUEST['object_id'], $info['objtype_id']))
135080d8 1684 return buildRedirectURL (__FUNCTION__, 'OK', array(), $pageno, 'ports');
f3f0161f 1685 else
135080d8 1686 return buildRedirectURL (__FUNCTION__, 'ERR');
f3f0161f
DO
1687}
1688
00e93d63 1689$msgcode['saveEntityTags']['OK'] = 26;
b6a7d936 1690$msgcode['saveEntityTags']['ERR1'] = 143;
24cbe8af 1691// Filter out implicit tags before storing the new tag set.
3355ca56 1692function saveEntityTags ()
24cbe8af 1693{
1d356026
DO
1694 global $pageno, $etype_by_pageno;
1695 if (!isset ($etype_by_pageno[$pageno]))
1696 throw new RackTablesError ('key not found in etype_by_pageno', RackTablesError::INTERNAL);
be2ae2a2 1697 $realm = $etype_by_pageno[$pageno];
1d356026 1698 $entity_id = getBypassValue();
e04931c8 1699 $taglist = isset ($_REQUEST['taglist']) ? $_REQUEST['taglist'] : array();
6e49bd1f 1700 // Build a chain from the submitted data, minimize it,
ab379543 1701 // then wipe existing records and store the new set instead.
01b6b4d6 1702 destroyTagsForEntity ($realm, $entity_id);
eb27afad
DO
1703 // TODO: these actions are very close to what rebuildTagChainForEntity() does,
1704 // so why not use it?
6e49bd1f 1705 $newchain = getExplicitTagsOnly (buildTagChainFromIds ($taglist));
ab379543 1706 $n_succeeds = $n_errors = 0;
6e49bd1f 1707 foreach ($newchain as $taginfo)
eb6ea26f 1708 if (addTagForEntity ($realm, $entity_id, $taginfo['id']))
ab379543
DO
1709 $n_succeeds++;
1710 else
1711 $n_errors++;
ab379543 1712 if ($n_errors)
9a61c175 1713 return buildRedirectURL (__FUNCTION__, 'ERR1', array ($n_succeeds, $n_errors));
ab379543 1714 else
135080d8 1715 return buildRedirectURL (__FUNCTION__, 'OK', array ($n_succeeds));
2034d968
DO
1716}
1717
b6a7d936
DO
1718$msgcode['rollTags']['OK'] = 67;
1719$msgcode['rollTags']['ERR'] = 149;
eb6ea26f
DO
1720function rollTags ()
1721{
0cc24e9a
DY
1722 assertStringArg ('sum', TRUE);
1723 assertUIntArg ('realsum');
eb6ea26f 1724 if ($_REQUEST['sum'] != $_REQUEST['realsum'])
135080d8 1725 return buildRedirectURL (__FUNCTION__, 'ERR');
abef7149
DO
1726 // Even if the user requested an empty tag list, don't bail out, but process existing
1727 // tag chains with "zero" extra. This will make sure, that the stuff processed will
1728 // have its chains refined to "normal" form.
1729 $extratags = isset ($_REQUEST['taglist']) ? $_REQUEST['taglist'] : array();
1730 $n_ok = 0;
1731 // Minimizing the extra chain early, so that tag rebuilder doesn't have to
1732 // filter out the same tag again and again. It will have own noise to cancel.
1733 $extrachain = getExplicitTagsOnly (buildTagChainFromIds ($extratags));
61a1d996 1734 foreach (listCells ('rack', $_REQUEST['row_id']) as $rack)
abef7149 1735 {
61a1d996 1736 if (rebuildTagChainForEntity ('rack', $rack['id'], $extrachain))
abef7149 1737 $n_ok++;
61a1d996
DO
1738 amplifyCell ($rack);
1739 foreach ($rack['mountedObjects'] as $object_id)
abef7149
DO
1740 if (rebuildTagChainForEntity ('object', $object_id, $extrachain))
1741 $n_ok++;
1742 }
135080d8 1743 return buildRedirectURL (__FUNCTION__, 'OK', array ($n_ok));
eb6ea26f
DO
1744}
1745
00e93d63 1746$msgcode['changeMyPassword']['OK'] = 51;
b6a7d936
DO
1747$msgcode['changeMyPassword']['ERR1'] = 150;
1748$msgcode['changeMyPassword']['ERR2'] = 151;
1749$msgcode['changeMyPassword']['ERR3'] = 152;
1750$msgcode['changeMyPassword']['ERR4'] = 153;
9457ca59 1751function changeMyPassword ()
cced6b7d 1752{
b82cce3f 1753 global $remote_username, $user_auth_src;
204284ba 1754 if ($user_auth_src != 'database')
135080d8 1755 return buildRedirectURL (__FUNCTION__, 'ERR1');
0cc24e9a
DY
1756 assertStringArg ('oldpassword');
1757 assertStringArg ('newpassword1');
1758 assertStringArg ('newpassword2');
b82cce3f 1759 $remote_userid = getUserIDByUsername ($remote_username);
0b2c74cb 1760 $userinfo = spotEntity ('user', $remote_userid);
b82cce3f 1761 if ($userinfo['user_password_hash'] != sha1 ($_REQUEST['oldpassword']))
135080d8 1762 return buildRedirectURL (__FUNCTION__, 'ERR2');
cced6b7d 1763 if ($_REQUEST['newpassword1'] != $_REQUEST['newpassword2'])
135080d8 1764 return buildRedirectURL (__FUNCTION__, 'ERR3');
32832c0e 1765 if (FALSE !== commitUpdateUserAccount ($remote_userid, $userinfo['user_name'], $userinfo['user_realname'], sha1 ($_REQUEST['newpassword1'])))
135080d8 1766 return buildRedirectURL (__FUNCTION__, 'OK');
cced6b7d 1767 else
135080d8 1768 return buildRedirectURL (__FUNCTION__, 'ERR4');
cced6b7d
DO
1769}
1770
b6a7d936
DO
1771$msgcode['saveRackCode']['OK'] = 43;
1772$msgcode['saveRackCode']['ERR1'] = 154;
1773$msgcode['saveRackCode']['ERR2'] = 155;
cced6b7d
DO
1774function saveRackCode ()
1775{
cced6b7d 1776 assertStringArg ('rackcode');
e6a4adb9 1777 // For the test to succeed, unescape LFs, strip CRs.
7f42d792 1778 $newcode = dos2unix ($_REQUEST['rackcode']);
cf25e649
DO
1779 $parseTree = getRackCode ($newcode);
1780 if ($parseTree['result'] != 'ACK')
135080d8 1781 return buildRedirectURL (__FUNCTION__, 'ERR1', array ($parseTree['load']));
bb09f49c
DO
1782 if (FALSE !== saveScript ('RackCode', $newcode))
1783 {
1784 saveScript ('RackCodeCache', base64_encode (serialize ($parseTree)));
135080d8 1785 return buildRedirectURL (__FUNCTION__, 'OK');
bb09f49c
DO
1786 }
1787 return buildRedirectURL (__FUNCTION__, 'ERR2');
cced6b7d
DO
1788}
1789
3f052a67 1790$msgcode['setPortVLAN']['ERR'] = 164;
46f92ff7
DO
1791// This handler's context is pre-built, but not authorized. It is assumed, that the
1792// handler will take existing context and before each commit check authorization
1793// on the base chain plus necessary context added.
1794function setPortVLAN ()
1795{
0cc24e9a 1796 assertUIntArg ('portcount');
3f052a67
DO
1797 try
1798 {
1799 $data = getSwitchVLANs ($_REQUEST['object_id']);
1800 }
1801 catch (RTGatewayError $re)
1802 {
1803 return buildRedirectURL (__FUNCTION__, 'ERR', array ($re->getMessage()));
1804 }
46f92ff7
DO
1805 list ($vlanlist, $portlist) = $data;
1806 // Here we just build up 1 set command for the gateway with all of the ports
1807 // included. The gateway is expected to filter unnecessary changes silently
1808 // and to provide a list of responses with either error or success message
1809 // for each of the rest.
1810 $nports = $_REQUEST['portcount'];
1811 $prefix = 'set ';
db55cf54 1812 $log = emptyLog();
46f92ff7
DO
1813 $setcmd = '';
1814 for ($i = 0; $i < $nports; $i++)
3f052a67
DO
1815 {
1816 genericAssertion ('portname_' . $i, 'string');
1817 genericAssertion ('vlanid_' . $i, 'string');
1818 if ($_REQUEST['portname_' . $i] != $portlist[$i]['portname'])
1819 throw new InvalidRequestArgException ('portname_' . $i, $_REQUEST['portname_' . $i], 'expected to be ' . $portlist[$i]['portname']);
46f92ff7 1820 if
46f92ff7
DO
1821 (
1822 $_REQUEST['vlanid_' . $i] == $portlist[$i]['vlanid'] ||
1823 $portlist[$i]['vlaind'] == 'TRUNK'
1824 )
1825 continue;
3f052a67
DO
1826 $portname = $_REQUEST['portname_' . $i];
1827 $oldvlanid = $portlist[$i]['vlanid'];
1828 $newvlanid = $_REQUEST['vlanid_' . $i];
1829 if
1830 (
1831 !permitted (NULL, NULL, NULL, array (array ('tag' => '$fromvlan_' . $oldvlanid))) or
1832 !permitted (NULL, NULL, NULL, array (array ('tag' => '$tovlan_' . $newvlanid)))
1833 )
46f92ff7 1834 {
1d84140d 1835 $log = mergeLogs ($log, oneLiner (159, array ($portname, $oldvlanid, $newvlanid)));
3f052a67 1836 continue;
46f92ff7 1837 }
3f052a67
DO
1838 $setcmd .= $prefix . $portname . '=' . $newvlanid;
1839 $prefix = ';';
1840 }
46f92ff7 1841 // Feed the gateway and interpret its (non)response.
1d84140d
DO
1842 if ($setcmd == '')
1843 $log = mergeLogs ($log, oneLiner (201));
46f92ff7 1844 else
1d84140d
DO
1845 {
1846 try
1847 {
1848 $log = mergeLogs ($log, setSwitchVLANs ($_REQUEST['object_id'], $setcmd));
1849 }
1850 catch (RTGatewayError $e)
1851 {
1852 $log = mergeLogs ($log, oneLiner (164, $e->getMessage()));
1853 }
1854 }
46f92ff7
DO
1855 return buildWideRedirectURL ($log);
1856}
1857
12b0c847
DO
1858$msgcode['submitSLBConfig']['OK'] = 66;
1859$msgcode['submitSLBConfig']['ERR'] = 164;
2987fc1f
DO
1860function submitSLBConfig ()
1861{
2987fc1f 1862 $newconfig = buildLVSConfig ($_REQUEST['object_id']);
12b0c847
DO
1863 try
1864 {
1865 gwSendFileToObject ($_REQUEST['object_id'], 'slbconfig', html_entity_decode ($newconfig, ENT_QUOTES, 'UTF-8'));
1866 }
3a089a44 1867 catch (RTGatewayError $e)
12b0c847 1868 {
3a089a44 1869 return buildRedirectURL (__FUNCTION__, 'ERR', array ($e->getMessage()));
12b0c847
DO
1870 }
1871 return buildRedirectURL (__FUNCTION__, 'OK', array ('slbconfig'));
2987fc1f
DO
1872}
1873
00e93d63 1874$msgcode['addRack']['OK'] = 51;
b6a7d936 1875$msgcode['addRack']['ERR2'] = 172;
f19c75d6
DO
1876function addRack ()
1877{
f19c75d6
DO
1878 $taglist = isset ($_REQUEST['taglist']) ? $_REQUEST['taglist'] : array();
1879 if (isset ($_REQUEST['got_data']))
1880 {
0cc24e9a
DY
1881 assertStringArg ('rack_name');
1882 assertUIntArg ('rack_height1');
1883 assertStringArg ('rack_comment', TRUE);
00e93d63
DO
1884 commitAddRack ($_REQUEST['rack_name'], $_REQUEST['rack_height1'], $_REQUEST['row_id'], $_REQUEST['rack_comment'], $taglist);
1885 return buildRedirectURL (__FUNCTION__, 'OK', array ($_REQUEST['rack_name']));
f19c75d6
DO
1886 }
1887 elseif (isset ($_REQUEST['got_mdata']))
1888 {
0cc24e9a
DY
1889 assertUIntArg ('rack_height2');
1890 assertStringArg ('rack_names', TRUE);
db55cf54 1891 $log = emptyLog();
f19c75d6 1892 // copy-and-paste from renderAddMultipleObjectsForm()
7f42d792 1893 $names1 = explode ("\n", $_REQUEST['rack_names']);
f19c75d6
DO
1894 $names2 = array();
1895 foreach ($names1 as $line)
1896 {
1897 $parts = explode ('\r', $line);
1898 reset ($parts);
59a83bd8 1899 if (!strlen ($parts[0]))
f19c75d6
DO
1900 continue;
1901 else
1902 $names2[] = rtrim ($parts[0]);
1903 }
b3029d5c 1904 global $msgcode;
f19c75d6 1905 foreach ($names2 as $cname)
1d84140d
DO
1906 {
1907 commitAddRack ($cname, $_REQUEST['rack_height2'], $_REQUEST['row_id'], '', $taglist);
1908 $log['m'][] = array ('c' => $msgcode[__FUNCTION__]['OK'], 'a' => array ($cname));
1909 }
f19c75d6
DO
1910 return buildWideRedirectURL ($log);
1911 }
1912 else
135080d8 1913 return buildRedirectURL (__FUNCTION__, 'ERR2');
f19c75d6
DO
1914}
1915
00e93d63 1916$msgcode['deleteRack']['OK'] = 6;
b6a7d936
DO
1917$msgcode['deleteRack']['ERR'] = 100;
1918$msgcode['deleteRack']['ERR1'] = 206;
c8187437
DY
1919function deleteRack ()
1920{
0cc24e9a 1921 assertUIntArg ('rack_id');
6538d363 1922 $rackData = spotEntity ('rack', $_REQUEST['rack_id']);
61a1d996
DO
1923 amplifyCell ($rackData);
1924 if (count ($rackData['mountedObjects']))
c8187437 1925 return buildRedirectURL (__FUNCTION__, 'ERR1');
61a1d996
DO
1926 if (TRUE !== commitDeleteRack ($_REQUEST['rack_id']))
1927 return buildRedirectURL (__FUNCTION__, 'ERR', array(), 'rackspace', 'default');
1928 return buildRedirectURL (__FUNCTION__, 'OK', array ($rackData['name']), 'rackspace', 'default');
c8187437
DY
1929}
1930
00e93d63
DO
1931$msgcode['updateRack']['OK'] = 7;
1932$msgcode['updateRack']['ERR'] = 109;
7056988c
DO
1933function updateRack ()
1934{
0cc24e9a
DY
1935 assertUIntArg ('rack_row_id');
1936 assertUIntArg ('rack_height');
1937 assertStringArg ('rack_name');
1938 assertStringArg ('rack_comment', TRUE);
7056988c 1939
7056988c 1940 resetThumbCache ($_REQUEST['rack_id']);
0c2b7c4a 1941 if (TRUE === commitUpdateRack ($_REQUEST['rack_id'], $_REQUEST['rack_name'], $_REQUEST['rack_height'], $_REQUEST['rack_row_id'], $_REQUEST['rack_comment']))
135080d8 1942 return buildRedirectURL (__FUNCTION__, 'OK', array ($_REQUEST['rack_name']));
0c2b7c4a 1943 else
135080d8 1944 return buildRedirectURL (__FUNCTION__, 'ERR');
7056988c
DO
1945}
1946
4fbb5a00
DY
1947function updateRackDesign ()
1948{
6cfedb71 1949 $rackData = spotEntity ('rack', $_REQUEST['rack_id']);
61a1d996 1950 amplifyCell ($rackData);
4fbb5a00
DY
1951 applyRackDesignMask($rackData);
1952 markupObjectProblems ($rackData);
1953 $response = processGridForm ($rackData, 'A', 'F');
51690ad4 1954 return buildWideRedirectURL (array($response));
4fbb5a00
DY
1955}
1956
1957function updateRackProblems ()
1958{
6cfedb71 1959 $rackData = spotEntity ('rack', $_REQUEST['rack_id']);
61a1d996 1960 amplifyCell ($rackData);
4fbb5a00
DY
1961 applyRackProblemMask($rackData);
1962 markupObjectProblems ($rackData);
1963 $response = processGridForm ($rackData, 'F', 'U');
51690ad4 1964 return buildWideRedirectURL (array($response));
4fbb5a00
DY
1965}
1966
7056988c
DO
1967function querySNMPData ()
1968{
8228bdb4
DO
1969 assertStringArg ('community', TRUE);
1970
1971 $snmpsetup = array ();
011b6699 1972 if ($_REQUEST['community'] != '')
1d84140d
DO
1973 $snmpsetup['community'] = $_REQUEST['community'];
1974 else
1975 {
8228bdb4
DO
1976 assertStringArg ('sec_name');
1977 assertStringArg ('sec_level');
1978 assertStringArg ('auth_protocol');
1979 assertStringArg ('auth_passphrase', TRUE);
1980 assertStringArg ('priv_protocol');
1981 assertStringArg ('priv_passphrase', TRUE);
1982
1983 $snmpsetup['sec_name'] = $_REQUEST['sec_name'];
1984 $snmpsetup['sec_level'] = $_REQUEST['sec_level'];
1985 $snmpsetup['auth_protocol'] = $_REQUEST['auth_protocol'];
1986 $snmpsetup['auth_passphrase'] = $_REQUEST['auth_passphrase'];
1987 $snmpsetup['priv_protocol'] = $_REQUEST['priv_protocol'];
1988 $snmpsetup['priv_passphrase'] = $_REQUEST['priv_passphrase'];
1989 }
8228bdb4 1990 return doSNMPmining ($_REQUEST['object_id'], $snmpsetup);
7056988c
DO
1991}
1992
00e93d63 1993$msgcode['addFileWithoutLink']['OK'] = 5;
6cfedb71 1994$msgcode['addFileWithoutLink']['ERR2'] = 110;
e1ae3fb4
AD
1995// File-related functions
1996function addFileWithoutLink ()
1997{
0cc24e9a 1998 assertStringArg ('comment', TRUE);
e1ae3fb4
AD
1999
2000 // Make sure the file can be uploaded
2001 if (get_cfg_var('file_uploads') != 1)
00e93d63 2002 throw new RackTablesError ('file uploads not allowed, change "file_uploads" parameter in php.ini', RackTablesError::MISCONFIGURED);
e1ae3fb4
AD
2003
2004 $fp = fopen($_FILES['file']['tmp_name'], 'rb');
4bb95650 2005 global $sic;
6cfedb71
DO
2006 if (FALSE === commitAddFile ($_FILES['file']['name'], $_FILES['file']['type'], $_FILES['file']['size'], $fp, $sic['comment']))
2007 return buildRedirectURL (__FUNCTION__, 'ERR2');
f857f71f
DO
2008 if (isset ($_REQUEST['taglist']))
2009 produceTagsForLastRecord ('file', $_REQUEST['taglist']);
6cfedb71 2010 return buildRedirectURL (__FUNCTION__, 'OK', array (htmlspecialchars ($_FILES['file']['name'])));
e1ae3fb4
AD
2011}
2012
00e93d63 2013$msgcode['addFileToEntity']['OK'] = 5;
b6a7d936 2014$msgcode['addFileToEntity']['ERR2'] = 181;
6cfedb71 2015$msgcode['addFileToEntity']['ERR3'] = 110;
e1ae3fb4
AD
2016function addFileToEntity ()
2017{
1d356026
DO
2018 global $pageno, $etype_by_pageno;
2019 if (!isset ($etype_by_pageno[$pageno]))
2020 throw new RackTablesError ('key not found in etype_by_pageno', RackTablesError::INTERNAL);
9a61c175 2021 $realm = $etype_by_pageno[$pageno];
1d356026 2022 $entity_id = getBypassValue();
0cc24e9a 2023 assertStringArg ('comment', TRUE);
e1ae3fb4
AD
2024
2025 // Make sure the file can be uploaded
2026 if (get_cfg_var('file_uploads') != 1)
9a61c175 2027 return buildRedirectURL (__FUNCTION__, 'ERR2');
e1ae3fb4
AD
2028
2029 $fp = fopen($_FILES['file']['tmp_name'], 'rb');
4bb95650 2030 global $sic;
6cfedb71
DO
2031 if (FALSE === commitAddFile ($_FILES['file']['name'], $_FILES['file']['type'], $_FILES['file']['size'], $fp, $sic['comment']))
2032 return buildRedirectURL (__FUNCTION__, 'ERR3');
2033 if (FALSE === commitLinkFile (lastInsertID(), $realm, $entity_id))
2034 return buildRedirectURL (__FUNCTION__, 'ERR3');
e1ae3fb4 2035
6cfedb71 2036 return buildRedirectURL (__FUNCTION__, 'OK', array (htmlspecialchars ($_FILES['file']['name'])));
e1ae3fb4
AD
2037}
2038
b6a7d936 2039$msgcode['linkFileToEntity']['OK'] = 71;
6cfedb71 2040$msgcode['linkFileToEntity']['ERR2'] = 110;
e1ae3fb4
AD
2041function linkFileToEntity ()
2042{
0cc24e9a 2043 assertUIntArg ('file_id');
1d356026
DO
2044 global $pageno, $etype_by_pageno;
2045 if (!isset ($etype_by_pageno[$pageno]))
2046 throw new RackTablesError ('key not found in etype_by_pageno', RackTablesError::INTERNAL);
121496b6 2047
d3b5008b 2048 $fi = spotEntity ('file', $_REQUEST['file_id']);
1d356026 2049 if (FALSE === commitLinkFile ($_REQUEST['file_id'], $etype_by_pageno[$pageno], getBypassValue()))
6cfedb71 2050 return buildRedirectURL (__FUNCTION__, 'ERR2');
e1ae3fb4 2051
6cfedb71 2052 return buildRedirectURL (__FUNCTION__, 'OK', array (htmlspecialchars ($fi['name'])));
e1ae3fb4
AD
2053}
2054
00e93d63 2055$msgcode['replaceFile']['OK'] = 7;
b6a7d936
DO
2056$msgcode['replaceFile']['ERR1'] = 181;
2057$msgcode['replaceFile']['ERR2'] = 207;
6cfedb71 2058$msgcode['replaceFile']['ERR3'] = 109;
fd1fb420
AD
2059function replaceFile ()
2060{
db55cf54 2061 global $sic;
fd1fb420
AD
2062
2063 // Make sure the file can be uploaded
2064 if (get_cfg_var('file_uploads') != 1)
db55cf54 2065 return buildRedirectURL (__FUNCTION__, 'ERR1');
d3b5008b 2066 $shortInfo = spotEntity ('file', $sic['file_id']);
fd1fb420
AD
2067
2068 $fp = fopen($_FILES['file']['tmp_name'], 'rb');
db55cf54
DO
2069 if ($fp === FALSE)
2070 return buildRedirectURL (__FUNCTION__, 'ERR2');
6cfedb71
DO
2071 if (FALSE === commitReplaceFile ($sic['file_id'], $fp))
2072 return buildRedirectURL (__FUNCTION__, 'ERR3');
fd1fb420 2073
d3346ce2
DO
2074 usePreparedExecuteBlade
2075 (
2076 'UPDATE File SET thumbnail = NULL WHERE id = ?',
2077 $sic['file_id']
2078 );
2079
db55cf54 2080 return buildRedirectURL (__FUNCTION__, 'OK', array (htmlspecialchars ($shortInfo['name'])));
fd1fb420
AD
2081}
2082
b6a7d936 2083$msgcode['updateFile']['OK'] = 70;
6cfedb71 2084$msgcode['updateFile']['ERR'] = 109;
e1ae3fb4
AD
2085function updateFile ()
2086{
0cc24e9a
DY
2087 assertStringArg ('file_name');
2088 assertStringArg ('file_type');
2089 assertStringArg ('file_comment', TRUE);
f3d274bf 2090 global $sic;
6cfedb71
DO
2091 if (FALSE === commitUpdateFile ($sic['file_id'], $sic['file_name'], $sic['file_type'], $sic['file_comment']))
2092 return buildRedirectURL (__FUNCTION__, 'ERR');
7221c918 2093 return buildRedirectURL (__FUNCTION__, 'OK', array ($_REQUEST['file_name']));
e1ae3fb4
AD
2094}
2095
b6a7d936 2096$msgcode['unlinkFile']['OK'] = 72;
00e93d63 2097$msgcode['unlinkFile']['ERR'] = 111;
e1ae3fb4
AD
2098function unlinkFile ()
2099{
0cc24e9a 2100 assertUIntArg ('link_id');
00e93d63 2101 return buildRedirectURL (__FUNCTION__, commitUnlinkFile ($_REQUEST['link_id']) === FALSE ? 'ERR' : 'OK');
e1ae3fb4
AD
2102}
2103
00e93d63 2104$msgcode['deleteFile']['OK'] = 6;
1d84140d 2105$msgcode['deleteFile']['ERR'] = 111;
e1ae3fb4
AD
2106function deleteFile ()
2107{
0cc24e9a 2108 assertUIntArg ('file_id');
d3b5008b 2109 $shortInfo = spotEntity ('file', $_REQUEST['file_id']);
e1ae3fb4
AD
2110 $error = commitDeleteFile ($_REQUEST['file_id']);
2111
2112 if ($error != '')
135080d8 2113 return buildRedirectURL (__FUNCTION__, 'ERR', array ($error));
e1ae3fb4 2114
f8874cdb 2115 return buildRedirectURL (__FUNCTION__, 'OK', array (htmlspecialchars ($shortInfo['name'])));
e1ae3fb4
AD
2116}
2117
00e93d63 2118$msgcode['updateFileText']['OK'] = 7;
b6a7d936 2119$msgcode['updateFileText']['ERR1'] = 179;
00e93d63 2120$msgcode['updateFileText']['ERR2'] = 155;
8628ae44
DO
2121function updateFileText ()
2122{
0cc24e9a
DY
2123 assertStringArg ('mtime_copy');
2124 assertStringArg ('file_text', TRUE); // it's Ok to save empty
d3b5008b 2125 $shortInfo = spotEntity ('file', $_REQUEST['file_id']);
70cb9b56
DO
2126 if ($shortInfo['mtime'] != $_REQUEST['mtime_copy'])
2127 return buildRedirectURL (__FUNCTION__, 'ERR1');
f8874cdb 2128 global $sic;
6cfedb71
DO
2129 if (FALSE === commitReplaceFile ($sic['file_id'], $sic['file_text']))
2130 return buildRedirectURL (__FUNCTION__, 'ERR2');
2131 return buildRedirectURL (__FUNCTION__, 'OK', array (htmlspecialchars ($shortInfo['name'])));
8628ae44
DO
2132}
2133
2dfa1b73
DO
2134$msgcode['addPortInterfaceCompat']['OK'] = 48;
2135$msgcode['addPortInterfaceCompat']['ERR'] = 110;
2136function addPortInterfaceCompat ()
2137{
0cc24e9a
DY
2138 assertUIntArg ('iif_id');
2139 assertUIntArg ('oif_id');
2dfa1b73
DO
2140 if (commitSupplementPIC ($_REQUEST['iif_id'], $_REQUEST['oif_id']))
2141 return buildRedirectURL (__FUNCTION__, 'OK');
2142 return buildRedirectURL (__FUNCTION__, 'ERR');
2143}
2144
2400d7ec
DO
2145$ifcompatpack = array
2146(
2147 '1000cwdm80' => array (1209, 1210, 1211, 1212, 1213, 1214, 1215, 1216),
2148 '1000dwdm80' => array // ITU channels 20~61
2149 (
2150 1217, 1218, 1219, 1220, 1221, 1222, 1223, 1224, 1225, 1226,
2151 1227, 1228, 1229, 1230, 1231, 1232, 1233, 1234, 1235, 1236,
2152 1237, 1238, 1239, 1240, 1241, 1242, 1243, 1244, 1245, 1246,
2153 1247, 1248, 1249, 1250, 1251, 1252, 1253, 1254, 1255, 1256,
2154 1257, 1258
2155 ),
2156 '10000dwdm80' => array // same channels for 10GE
2157 (
2158 1259, 1260, 1261, 1262, 1263, 1264, 1265, 1266, 1267, 1268,
2159 1269, 1270, 1271, 1272, 1273, 1274, 1275, 1276, 1277, 1278,
2160 1279, 1280, 1281, 1282, 1283, 1284, 1285, 1286, 1287, 1288,
2161 1289, 1290, 1291, 1292, 1293, 1294, 1295, 1296, 1297, 1298,
2162 1299, 1300
2163 ),
2164);
2165
3d9ac3d4 2166$msgcode['addPortInterfaceCompatPack']['OK'] = 44;
2400d7ec
DO
2167function addPortInterfaceCompatPack ()
2168{
00e93d63
DO
2169 genericAssertion ('standard', 'enum/wdmstd');
2170 genericAssertion ('iif_id', 'iif');
3d9ac3d4 2171 global $ifcompatpack;
3d9ac3d4
DO
2172 $ngood = $nbad = 0;
2173 foreach ($ifcompatpack[$_REQUEST['standard']] as $oif_id)
2174 if (commitSupplementPIC ($_REQUEST['iif_id'], $oif_id))
2175 $ngood++;
2176 else
2177 $nbad++;
2178 return buildRedirectURL (__FUNCTION__, 'OK', array ($nbad, $ngood));
2400d7ec
DO
2179}
2180
3d9ac3d4
DO
2181$msgcode['delPortInterfaceCompatPack']['OK'] = 44;
2182$msgcode['delPortInterfaceCompatPack']['ERR'] = 123;
2400d7ec
DO
2183function delPortInterfaceCompatPack ()
2184{
0cc24e9a
DY
2185 assertStringArg ('standard');
2186 assertUIntArg ('iif_id');
10005279
DO
2187 global $ifcompatpack, $sic;
2188 if (!array_key_exists ($sic['standard'], $ifcompatpack) or !array_key_exists ($sic['iif_id'], getPortIIFOptions()))
3d9ac3d4
DO
2189 return buildRedirectURL (__FUNCTION__, 'ERR');
2190 $ngood = $nbad = 0;
10005279
DO
2191 foreach ($ifcompatpack[$sic['standard']] as $oif_id)
2192 if (usePreparedDeleteBlade ('PortInterfaceCompat', array ('iif_id' => $sic['iif_id'], 'oif_id' => $oif_id)))
3d9ac3d4
DO
2193 $ngood++;
2194 else
2195 $nbad++;
2196 return buildRedirectURL (__FUNCTION__, 'OK', array ($nbad, $ngood));
2400d7ec
DO
2197}
2198
38cd7704 2199$msgcode['add8021QOrder']['OK'] = 48;
00e93d63 2200$msgcode['add8021QOrder']['ERR'] = 110;
38cd7704 2201function add8021QOrder ()
8198f2c6 2202{
80ec1f4f
DO
2203 assertUIntArg ('vdom_id');
2204 assertUIntArg ('object_id');
38cd7704 2205 assertUIntArg ('vst_id');
c1aa3ada
DO
2206 global $sic;
2207 $result = usePreparedExecuteBlade
8198f2c6 2208 (
c1aa3ada
DO
2209 'INSERT INTO VLANSwitch (domain_id, object_id, template_id, last_change, out_of_sync) ' .
2210 'VALUES (?, ?, ?, NOW(), "yes")',
2211 array ($sic['vdom_id'], $sic['object_id'], $sic['vst_id'])
8198f2c6 2212 );
c1aa3ada 2213 return buildRedirectURL (__FUNCTION__, $result !== FALSE ? 'OK' : 'ERR');
8198f2c6
DO
2214}
2215
38cd7704 2216$msgcode['del8021QOrder']['OK'] = 49;
00e93d63 2217$msgcode['del8021QOrder']['ERR'] = 111;
38cd7704 2218function del8021QOrder ()
8198f2c6 2219{
80ec1f4f 2220 assertUIntArg ('object_id');
4191d7ab
AA
2221 assertUIntArg ('vdom_id');
2222 assertUIntArg ('vst_id');
8198f2c6 2223 global $sic;
38cd7704 2224 $result = usePreparedDeleteBlade ('VLANSwitch', array ('object_id' => $sic['object_id']));
4191d7ab
AA
2225 $focus_hints = array
2226 (
2227 'prev_objid' => $_REQUEST['object_id'],
2228 'prev_vstid' => $_REQUEST['vst_id'],
2229 'prev_vdid' => $_REQUEST['vdom_id'],
2230 );
2231 return buildRedirectURL (__FUNCTION__, $result ? 'OK' : 'ERR', array(), NULL, NULL, $focus_hints);
8198f2c6
DO
2232}
2233
8198f2c6 2234$msgcode['delVLANDescription']['OK'] = 49;
c48f2e18
DO
2235$msgcode['delVLANDescription']['ERR1'] = 105;
2236$msgcode['delVLANDescription']['ERR2'] = 111;
8198f2c6
DO
2237function delVLANDescription ()
2238{
80ec1f4f 2239 assertUIntArg ('vlan_id');
8198f2c6 2240 global $sic;
c48f2e18 2241 if ($sic['vlan_id'] == VLAN_DFL_ID)
048b0420 2242 return buildRedirectURL (__FUNCTION__, 'ERR1');
8198f2c6 2243 $result = commitReduceVLANDescription ($sic['vdom_id'], $sic['vlan_id']);
c48f2e18 2244 return buildRedirectURL (__FUNCTION__, $result ? 'OK' : 'ERR2');
8198f2c6
DO
2245}
2246
2247$msgcode['updVLANDescription']['OK'] = 51;
c48f2e18
DO
2248$msgcode['updVLANDescription']['ERR1'] = 105;
2249$msgcode['updVLANDescription']['ERR2'] = 109;
8198f2c6
DO
2250function updVLANDescription ()
2251{
80ec1f4f
DO
2252 assertUIntArg ('vlan_id');
2253 assertStringArg ('vlan_type');
2254 assertStringArg ('vlan_descr', TRUE);
8198f2c6 2255 global $sic;
c48f2e18 2256 if ($sic['vlan_id'] == VLAN_DFL_ID)
048b0420 2257 return buildRedirectURL (__FUNCTION__, 'ERR1');
8198f2c6
DO
2258 $result = commitUpdateVLANDescription
2259 (
2260 $sic['vdom_id'],
2261 $sic['vlan_id'],
0dabdc53 2262 $sic['vlan_type'],
8198f2c6
DO
2263 $sic['vlan_descr']
2264 );
6cfedb71 2265 return buildRedirectURL (__FUNCTION__, $result !== FALSE ? 'OK' : 'ERR2');
8198f2c6
DO
2266}
2267
2268$msgcode['createVLANDomain']['OK'] = 48;
2269$msgcode['createVLANDomain']['ERR'] = 110;
2270function createVLANDomain ()
2271{
80ec1f4f 2272 assertStringArg ('vdom_descr');
8198f2c6
DO
2273 global $sic;
2274 $result = usePreparedInsertBlade
2275 (
2276 'VLANDomain',
2277 array
2278 (
2279 'description' => $sic['vdom_descr'],
2280 )
2281 );
10c7f49e
DO
2282 $result = $result and usePreparedInsertBlade
2283 (
2284 'VLANDescription',
2285 array
2286 (
2287 'domain_id' => lastInsertID(),
2288 'vlan_id' => VLAN_DFL_ID,
2289 'vlan_type' => 'compulsory',
c48f2e18 2290 'vlan_descr' => 'default',
10c7f49e
DO
2291 )
2292 );
8198f2c6
DO
2293 return buildRedirectURL (__FUNCTION__, $result ? 'OK' : 'ERR');
2294}
2295
2296$msgcode['destroyVLANDomain']['OK'] = 49;
2297$msgcode['destroyVLANDomain']['ERR'] = 111;
2298function destroyVLANDomain ()
2299{
80ec1f4f 2300 assertUIntArg ('vdom_id');
8198f2c6 2301 global $sic;
bbae3611 2302 $result = FALSE !== usePreparedDeleteBlade ('VLANDomain', array ('id' => $sic['vdom_id']));
8198f2c6
DO
2303 return buildRedirectURL (__FUNCTION__, $result ? 'OK' : 'ERR');
2304}
2305
2306$msgcode['updateVLANDomain']['OK'] = 51;
2307$msgcode['updateVLANDomain']['ERR'] = 109;
2308function updateVLANDomain ()
2309{
80ec1f4f
DO
2310 assertUIntArg ('vdom_id');
2311 assertStringArg ('vdom_descr');
8198f2c6 2312 global $sic;
d3192636 2313 $result = FALSE !== commitUpdateVLANDomain ($sic['vdom_id'], $sic['vdom_descr']);
8198f2c6
DO
2314 return buildRedirectURL (__FUNCTION__, $result ? 'OK' : 'ERR');
2315}
2316
4492050b
DO
2317$msgcode['save8021QPorts']['OK1'] = 63;
2318$msgcode['save8021QPorts']['OK2'] = 41;
706d9175
DO
2319$msgcode['save8021QPorts']['ERR2'] = 109;
2320function save8021QPorts ()
8198f2c6 2321{
a7492e95 2322 global $sic, $dbxlink;
70cff23f 2323 assertUIntArg ('mutex_rev', TRUE); // counts from 0
de8aa722
DO
2324 assertStringArg ('form_mode');
2325 if ($sic['form_mode'] != 'save' and $sic['form_mode'] != 'duplicate')
2326 throw new InvalidRequestArgException ('form_mode', $sic['form_mode']);
2327 $extra = array();
a7492e95 2328 $dbxlink->beginTransaction();
2996cbbb
DO
2329 try
2330 {
a7492e95
DO
2331 if (NULL === $vswitch = getVLANSwitchInfo ($sic['object_id'], 'FOR UPDATE'))
2332 throw new InvalidArgException ('object_id', $object_id, 'VLAN domain is not set for this object');
9c45ea37 2333 if ($vswitch['mutex_rev'] != $sic['mutex_rev'])
1a43ce88 2334 throw new InvalidRequestArgException ('mutex_rev', $sic['mutex_rev'], 'expired form data');
de8aa722 2335 $after = $before = apply8021QOrder ($vswitch['template_id'], getStored8021QConfig ($sic['object_id'], 'desired'));
af204724 2336 $changes = array();
de8aa722 2337 switch ($sic['form_mode'])
706d9175 2338 {
de8aa722
DO
2339 case 'save':
2340 assertUIntArg ('nports');
2341 if ($sic['nports'] == 1)
706d9175 2342 {
de8aa722
DO
2343 assertStringArg ('pn_0');
2344 $extra = array ('port_name' => $sic['pn_0']);
2345 }
2346 for ($i = 0; $i < $sic['nports']; $i++)
2347 {
2348 assertStringArg ('pn_' . $i);
2349 assertStringArg ('pm_' . $i);
2350 // An access port only generates form input for its native VLAN,
2351 // which we derive allowed VLAN list from.
2352 $native = isset ($sic['pnv_' . $i]) ? $sic['pnv_' . $i] : 0;
2353 switch ($sic["pm_${i}"])
2354 {
2355 case 'trunk':
b36fc896 2356# assertArrayArg ('pav_' . $i);
de8aa722
DO
2357 $allowed = isset ($sic['pav_' . $i]) ? $sic['pav_' . $i] : array();
2358 break;
2359 case 'access':
2360 if ($native == 'same')
2361 continue 2;
2362 assertUIntArg ('pnv_' . $i);
2363 $allowed = array ($native);
2364 break;
2365 default:
2366 throw new InvalidRequestArgException ("pm_${i}", $_REQUEST["pm_${i}"], 'unknown port mode');
2367 }
2368 $changes[$sic['pn_' . $i]] = array
2369 (
2370 'mode' => $sic['pm_' . $i],
2371 'allowed' => $allowed,
2372 'native' => $native,
2373 );
706d9175 2374 }
de8aa722
DO
2375 break;
2376 case 'duplicate':
2377 assertStringArg ('from_port');
2378# assertArrayArg ('to_ports');
2379 if (!array_key_exists ($sic['from_port'], $before))
2380 throw new InvalidArgException ('from_port', $sic['from_port'], 'this port does not exist');
2381 foreach ($sic['to_ports'] as $tpn)
2382 if (!array_key_exists ($tpn, $before))
2383 throw new InvalidArgException ('to_ports[]', $tpn, 'this port does not exist');
2384 elseif ($tpn != $sic['from_port'])
2385 $changes[$tpn] = $before[$sic['from_port']];
2386 break;
706d9175 2387 }
af204724
DO
2388 $domain_vlanlist = getDomainVLANs ($vswitch['domain_id']);
2389 $changes = filter8021QChangeRequests
a7492e95 2390 (
af204724 2391 $domain_vlanlist,
9165e8f7 2392 $before,
af204724 2393 apply8021QOrder ($vswitch['template_id'], $changes)
a7492e95 2394 );
bb2024b9 2395 $changes = authorize8021QChangeRequests ($before, $changes);
af204724
DO
2396 foreach ($changes as $port_name => $port)
2397 $after[$port_name] = $port;
b3a27170 2398 $new_uplinks = filter8021QChangeRequests ($domain_vlanlist, $after, produceUplinkPorts ($domain_vlanlist, $after));
7455e4c0 2399 $npulled = replace8021QPorts ('desired', $vswitch['object_id'], $before, $changes);
b3a27170 2400 $nsaved_uplinks = replace8021QPorts ('desired', $vswitch['object_id'], $before, $new_uplinks);
2996cbbb
DO
2401 }
2402 catch (Exception $e)
861292ee 2403 {
a7492e95 2404 $dbxlink->rollBack();
706d9175 2405 return buildRedirectURL (__FUNCTION__, 'ERR2', array(), NULL, NULL, $extra);
861292ee 2406 }
b3a27170 2407 if ($npulled + $nsaved_uplinks)
c1aa3ada
DO
2408 $result = usePreparedExecuteBlade
2409 (
2410 'UPDATE VLANSwitch SET mutex_rev=mutex_rev+1, last_change=NOW(), out_of_sync="yes" WHERE object_id=?',
2411 array ($sic['object_id'])
2412 );
a7492e95 2413 $dbxlink->commit();
4492050b 2414 $log = oneLiner (63, array ($npulled + $nsaved_uplinks));
b3a27170 2415 if ($nsaved_uplinks)
4492050b 2416 {
b3a27170 2417 initiateUplinksReverb ($vswitch['object_id'], $new_uplinks);
4492050b
DO
2418 $log = mergeLogs ($log, oneLiner (41));
2419 }
2420 if ($npulled + $nsaved_uplinks > 0 and getConfigVar ('8021Q_INSTANT_DEPLOY') == 'yes')
2421 {
2422 try
2423 {
2424 if (FALSE === $done = exec8021QDeploy ($sic['object_id'], TRUE))
2425 $log = mergeLogs ($log, oneLiner (191));
2426 else
2427 $log = mergeLogs ($log, oneLiner (63, array ($done)));
2428 }
2429 catch (Exception $e)
2430 {
2431 $log = mergeLogs ($log, oneLiner (109));
2432 }
2433 }
2434 return buildWideRedirectURL ($log, NULL, NULL, $extra);
8198f2c6
DO
2435}
2436
8846b060
DO
2437$msgcode['bindVLANtoIPv4']['OK'] = 48;
2438$msgcode['bindVLANtoIPv4']['ERR'] = 110;
2439function bindVLANtoIPv4 ()
2440{
2441 assertUIntArg ('id'); // network id
2442 global $sic;
2443 $result = commitSupplementVLANIPv4 ($sic['vlan_ck'], $sic['id']);
2444 return buildRedirectURL (__FUNCTION__, $result ? 'OK' : 'ERR');
2445}
2446
21ee3351
AA
2447$msgcode['bindVLANtoIPv6']['OK'] = 48;
2448$msgcode['bindVLANtoIPv6']['ERR'] = 110;
2449function bindVLANtoIPv6 ()
2450{
2451 assertUIntArg ('id'); // network id
2452 global $sic;
2453 $result = commitSupplementVLANIPv6 ($sic['vlan_ck'], $_REQUEST['id']);
2454 return buildRedirectURL (__FUNCTION__, $result ? 'OK' : 'ERR');
2455}
2456
8846b060
DO
2457$msgcode['unbindVLANfromIPv4']['OK'] = 49;
2458$msgcode['unbindVLANfromIPv4']['ERR'] = 111;
2459function unbindVLANfromIPv4 ()
2460{
2461 assertUIntArg ('id'); // network id
2462 global $sic;
2463 $result = commitReduceVLANIPv4 ($sic['vlan_ck'], $sic['id']);
2464 return buildRedirectURL (__FUNCTION__, $result ? 'OK' : 'ERR');
2465}
2466
21ee3351
AA
2467$msgcode['unbindVLANfromIPv6']['OK'] = 49;
2468$msgcode['unbindVLANfromIPv6']['ERR'] = 111;
2469function unbindVLANfromIPv6 ()
2470{
2471 assertUIntArg ('id'); // network id
2472 global $sic;
2473 $result = commitReduceVLANIPv6 ($sic['vlan_ck'], $sic['id']);
2474 return buildRedirectURL (__FUNCTION__, $result ? 'OK' : 'ERR');
2475}
2476
228c430c 2477$msgcode['process8021QSyncRequest']['OK'] = 63;
ec523868 2478$msgcode['process8021QSyncRequest']['ERR'] = 191;
228c430c 2479function process8021QSyncRequest ()
be28b696 2480{
2e84a05b
DO
2481 // behave depending on current operation: exec8021QPull or exec8021QPush
2482 global $sic, $op;
ec523868
DO
2483 if (FALSE === $done = exec8021QDeploy ($sic['object_id'], $op == 'exec8021QPush'))
2484 return buildRedirectURL (__FUNCTION__, 'ERR');
2485 return buildRedirectURL (__FUNCTION__, 'OK', array ($done));
be28b696
DO
2486}
2487
f9428bc6
AA
2488$msgcode['process8021QRecalcRequest']['CHANGED'] = 87;
2489$msgcode['process8021QRecalcRequest']['NO_CHANGES'] = 300;
00e93d63 2490$msgcode['process8021QRecalcRequest']['ERR'] = 157;
f9428bc6
AA
2491function process8021QRecalcRequest ()
2492{
f9428bc6 2493 global $sic;
fb3e3731
AA
2494 if (! permitted (NULL, NULL, NULL, array (array ('tag' => '$op_recalc8021Q'))))
2495 return buildRedirectURL (__FUNCTION__, 'ERR');
f9428bc6
AA
2496 $counters = recalc8021QPorts ($sic['object_id']);
2497 if ($counters['ports'])
2498 return buildRedirectURL (__FUNCTION__, 'CHANGED', array ($counters['ports'], $counters['switches']));
2499 else
2500 return buildRedirectURL (__FUNCTION__, 'NO_CHANGES', array ('No changes were made'));
2501}
2502
be28b696 2503$msgcode['resolve8021QConflicts']['OK'] = 63;
bcd14540
DO
2504$msgcode['resolve8021QConflicts']['ERR1'] = 179;
2505$msgcode['resolve8021QConflicts']['ERR2'] = 109;
be28b696 2506function resolve8021QConflicts ()
07de6bb3 2507{
a7492e95 2508 global $sic, $dbxlink;
70cff23f 2509 assertUIntArg ('mutex_rev', TRUE); // counts from 0
de47b574
DO
2510 assertUIntArg ('nrows');
2511 // Divide submitted radio buttons into 3 groups:
19d1e731 2512 // left (saved version wins)
07de6bb3 2513 // asis (ignore)
19d1e731
DO
2514 // right (running version wins)
2515 $F = array();
339534a0 2516 for ($i = 0; $i < $sic['nrows']; $i++)
07de6bb3 2517 {
de47b574 2518 if (!array_key_exists ("i_${i}", $sic))
07de6bb3 2519 continue;
de47b574
DO
2520 // let's hope other inputs are in place
2521 switch ($sic["i_${i}"])
07de6bb3
DO
2522 {
2523 case 'left':
07de6bb3 2524 case 'right':
bcd14540 2525 $F[$sic["pn_${i}"]] = array
07de6bb3 2526 (
ca9e1c9d 2527 'mode' => $sic["rm_${i}"],
de47b574
DO
2528 'allowed' => $sic["ra_${i}"],
2529 'native' => $sic["rn_${i}"],
bcd14540 2530 'decision' => $sic["i_${i}"],
07de6bb3
DO
2531 );
2532 break;
2533 default:
2534 // don't care
2535 }
2536 }
a7492e95 2537 $dbxlink->beginTransaction();
07de6bb3
DO
2538 try
2539 {
a7492e95 2540 if (NULL === $vswitch = getVLANSwitchInfo ($sic['object_id'], 'FOR UPDATE'))
ec4d604c 2541 throw new InvalidArgException ('object_id', $sic['object_id'], 'VLAN domain is not set for this object');
9c45ea37 2542 if ($vswitch['mutex_rev'] != $sic['mutex_rev'])
1a43ce88 2543 throw new InvalidRequestArgException ('mutex_rev', $sic['mutex_rev'], 'expired form (table data has changed)');
9c2201ba
DO
2544 $D = getStored8021QConfig ($vswitch['object_id'], 'desired');
2545 $C = getStored8021QConfig ($vswitch['object_id'], 'cached');
2546 $R = getRunning8021QConfig ($vswitch['object_id']);
d5e306b2 2547 $plan = get8021QSyncOptions ($vswitch, $D, $C, $R['portdata']);
bcd14540
DO
2548 $ndone = 0;
2549 foreach ($F as $port_name => $port)
2550 {
9c2201ba
DO
2551 if (!array_key_exists ($port_name, $plan))
2552 continue;
2553 elseif ($plan[$port_name]['status'] == 'merge_conflict')
bcd14540 2554 {
9c2201ba
DO
2555 // for R neither mutex nor revisions can be emulated, but revision change can be
2556 if (!same8021QConfigs ($port, $R['portdata'][$port_name]))
1a43ce88 2557 throw new InvalidRequestArgException ("port ${port_name}", '(hidden)', 'expired form (switch data has changed)');
1f8f67c2 2558 if ($port['decision'] == 'right') // D wins, frame R by writing value of R to C
9c2201ba 2559 $ndone += upd8021QPort ('cached', $vswitch['object_id'], $port_name, $port);
1f8f67c2 2560 elseif ($port['decision'] == 'left') // R wins, cross D up
9c2201ba
DO
2561 $ndone += upd8021QPort ('cached', $vswitch['object_id'], $port_name, $D[$port_name]);
2562 // otherwise there was no decision made
2563 }
1f8f67c2
DO
2564 elseif
2565 (
2566 $plan[$port_name]['status'] == 'delete_conflict' or
2567 $plan[$port_name]['status'] == 'martian_conflict'
2568 )
9c2201ba 2569 {
1f8f67c2 2570 if ($port['decision'] == 'left') // confirm deletion of local copy
9c2201ba 2571 $ndone += del8021QPort ($vswitch['object_id'], $port_name);
bcd14540 2572 }
9c2201ba 2573 // otherwise ignore a decision, which doesn't address a conflict
bcd14540 2574 }
07de6bb3 2575 }
1a43ce88 2576 catch (InvalidRequestArgException $e)
07de6bb3 2577 {
a7492e95 2578 $dbxlink->rollBack();
bcd14540 2579 return buildRedirectURL (__FUNCTION__, 'ERR1');
ec4d604c 2580 }
bcd14540 2581 catch (Exception $e)
ec4d604c 2582 {
bcd14540
DO
2583 $dbxlink->rollBack();
2584 return buildRedirectURL (__FUNCTION__, 'ERR2');
ec4d604c 2585 }
a7492e95 2586 $dbxlink->commit();
bcd14540 2587 return buildRedirectURL (__FUNCTION__, 'OK', array ($ndone));
07de6bb3
DO
2588}
2589
e0d188ef
DO
2590$msgcode['addVLANSwitchTemplate']['OK'] = 48;
2591$msgcode['addVLANSwitchTemplate']['ERR'] = 110;
2592function addVLANSwitchTemplate()
2593{
2594 assertStringArg ('vst_descr');
2595 global $sic;
2596 $max_local_vlans = NULL;
2597 if (array_key_exists ('vst_maxvlans', $sic) && mb_strlen ($sic['vst_maxvlans']))
2598 {
2599 assertUIntArg ('vst_maxvlans');
2600 $max_local_vlans = $sic['vst_maxvlans'];
2601 }
2602 $result = usePreparedInsertBlade
2603 (
2604 'VLANSwitchTemplate',
2605 array
2606 (
2607 'max_local_vlans' => $max_local_vlans,
2608 'description' => $sic['vst_descr'],
2609 )
2610 );
2611 return buildRedirectURL (__FUNCTION__, $result ? 'OK' : 'ERR');
2612}
2613
2614$msgcode['delVLANSwitchTemplate']['OK'] = 49;
2615$msgcode['delVLANSwitchTemplate']['ERR'] = 111;
2616function delVLANSwitchTemplate()
2617{
2618 assertUIntArg ('vst_id');
2619 global $sic;
2620 $result = FALSE !== usePreparedDeleteBlade ('VLANSwitchTemplate', array ('id' => $sic['vst_id']));
2621 return buildRedirectURL (__FUNCTION__, $result ? 'OK' : 'ERR');
2622}
2623
2624$msgcode['updVLANSwitchTemplate']['OK'] = 51;
2625$msgcode['updVLANSwitchTemplate']['ERR'] = 109;
2626function updVLANSwitchTemplate()
2627{
2628 assertUIntArg ('vst_id');
2629 assertStringArg ('vst_descr');
2630 global $sic;
2631 $max_local_vlans = NULL;
2632 if (array_key_exists ('vst_maxvlans', $sic) && mb_strlen ($sic['vst_maxvlans']))
2633 {
2634 assertUIntArg ('vst_maxvlans');
2635 $max_local_vlans = $sic['vst_maxvlans'];
2636 }
2637 $result = commitUpdateVST ($sic['vst_id'], $max_local_vlans, $sic['vst_descr']);
6cfedb71 2638 return buildRedirectURL (__FUNCTION__, $result !== FALSE ? 'OK' : 'ERR');
e0d188ef
DO
2639}
2640
09ec2e59
AA
2641$msgcode['cloneVSTRule']['OK'] = 48;
2642$msgcode['cloneVSTRule']['ERR'] = 179;
2643function cloneVSTRule()
e0d188ef 2644{
09ec2e59
AA
2645 global $dbxlink;
2646 $message = '';
09ec2e59
AA
2647 assertUIntArg ('mutex_rev', TRUE);
2648 $dst_vst = getVLANSwitchTemplate ($_REQUEST['vst_id']);
2649 if ($dst_vst['mutex_rev'] != $_REQUEST['mutex_rev'])
2650 $message = "User ${dst_vst['saved_by']} saved this template after you started to edit it. Please concern differencies";
2651 else
eb51ceff 2652 {
eb51ceff
DO
2653 assertUIntArg ('from_id');
2654 $src_vst = getVLANSwitchTemplate ($_REQUEST['from_id']);
09ec2e59
AA
2655 if (! commitUpdateVSTRules ($_REQUEST['vst_id'], $src_vst['rules']))
2656 $message = 'DB error';
eb51ceff 2657 }
09ec2e59
AA
2658 $result = !(BOOL) $message;
2659 if ($result)
2660 $message = 'Supplement succeeded';
2661 return buildWideRedirectURL (array (array ('code' => $result ? 'success' : 'error', 'message' => $message)));
e0d188ef
DO
2662}
2663
405ac32c 2664$msgcode['updVSTRule']['OK'] = 43;
e0d188ef
DO
2665function updVSTRule()
2666{
405ac32c 2667 global $port_role_options, $sic;
09ec2e59 2668 assertUIntArg ('mutex_rev', TRUE);
405ac32c
DO
2669 genericAssertion ('template_json', 'json');
2670 $data = json_decode ($sic['template_json'], TRUE);
2671 $rule_no = 0;
2672 try
09ec2e59 2673 {
09ec2e59
AA
2674 foreach ($data as $rule)
2675 {
2676 $rule_no++;
405ac32c
DO
2677 if
2678 (
2679 ! isInteger ($rule['rule_no'])
2680 or ! isPCRE ($rule['port_pcre'])
2681 or ! isset ($rule['port_role'])
2682 or ! array_key_exists ($rule['port_role'], $port_role_options)
2683 or ! isset ($rule['wrt_vlans'])
2684 or ! preg_match ('/^[ 0-9\-,]*$/', $rule['wrt_vlans'])
2685 or ! isset ($rule['description'])
2686 )
2687 throw new InvalidRequestArgException ('form', '(JSON)', "invalid rule #$rule_no");
09ec2e59 2688 }
405ac32c 2689 commitUpdateVSTRules ($_REQUEST['vst_id'], $_REQUEST['mutex_rev'], $data);
09ec2e59 2690 }
405ac32c 2691 catch (Exception $e)
09ec2e59 2692 {
405ac32c
DO
2693 // Every case, which is soft-processed in process.php, will have the working copy available for a retry.
2694 if ($e instanceof InvalidRequestArgException or $e instanceof RTDatabaseError)
2695 $_SESSION['vst_edited'] = $data;
2696 throw $e;
09ec2e59 2697 }
405ac32c 2698 return buildRedirectURL (__FUNCTION__, 'OK');
e0d188ef
DO
2699}
2700
5b5b1cab
DO
2701$msgcode['importDPData']['OK'] = 44;
2702function importDPData()
b3247480
DO
2703{
2704 global $sic;
2705 assertUIntArg ('nports');
2706 $nignored = $ndone = 0;
1dc057f8 2707 $POIFC = getPortOIFCompat();
b3247480
DO
2708 for ($i = 0; $i < $sic['nports']; $i++)
2709 if (array_key_exists ("do_${i}", $sic))
2710 {
2711 assertUIntArg ("pid1_${i}");
2712 assertUIntArg ("pid2_${i}");
2713 $porta = getPortInfo ($_REQUEST["pid1_${i}"]);
2714 $portb = getPortInfo ($_REQUEST["pid2_${i}"]);
2715 if
2716 (
2717 $porta['linked'] or
2718 $portb['linked'] or
2719 ($porta['object_id'] != $sic['object_id'] and $portb['object_id'] != $sic['object_id'])
2720 )
2721 {
2722 $nignored++;
2723 continue;
2724 }
1dc057f8
DO
2725 foreach ($POIFC as $item)
2726 if ($item['type1'] == $porta['oif_id'] and $item['type2'] == $portb['oif_id'])
2727 {
2728 linkPorts ($_REQUEST["pid1_${i}"], $_REQUEST["pid2_${i}"]);
2729 $ndone++;
524170a8 2730 continue 2; // next port
1dc057f8
DO
2731 }
2732 $nignored++;
b3247480
DO
2733 }
2734 return buildRedirectURL (__FUNCTION__, 'OK', array ($nignored, $ndone));
2735}
2736
9a90adc4
DO
2737$msgcode['addObjectlog']['OK'] = 0;
2738function addObjectlog ()
2739{
9a90adc4
DO
2740 assertStringArg ('logentry');
2741 global $remote_username, $sic;
2742 $oi = spotEntity ('object', $sic['object_id']);
2743 usePreparedExecuteBlade ('INSERT INTO ObjectLog SET object_id=?, user=?, date=NOW(), content=?', array ($sic['object_id'], $remote_username, $sic['logentry']));
2744 $ob_url = makeHref (array ('page' => 'object', 'tab' => 'objectlog', 'object_id' => $sic['object_id']));
2745 return buildRedirectURL (__FUNCTION__, 'OK', array ("Log entry for <a href=" . ${ob_url} . ">${oi['dname']}</a> added by ${remote_username}"));
2746}
2747
e38cd1da
DO
2748function getOpspec()
2749{
2750 global $pageno, $tabno, $op, $opspec_list;
2751 if (!array_key_exists ($pageno . '-' . $tabno . '-' . $op, $opspec_list))
2752 throw new RackTablesError ('key not found in opspec_list', RackTablesError::INTERNAL);
2753 $ret = $opspec_list[$pageno . '-' . $tabno . '-' . $op];
2754 if
2755 (
2756 !array_key_exists ('table', $ret)
2757 or !array_key_exists ('action', $ret)
2758 // add further checks here
2759 )
2760 throw new RackTablesError ('malformed array structure in opspec_list', RackTablesError::INTERNAL);
2761 return $ret;
2762}
2763
2764function tableHandler()
cde28cf0 2765{
548c9349 2766 $opspec = getOpspec();
cde28cf0 2767 global $sic;
cde28cf0 2768 $columns = array();
09ecff69
DO
2769 foreach (array ('arglist', 'set_arglist', 'where_arglist') as $listname)
2770 foreach ($opspec[$listname] as $argspec)
2771 {
2772 genericAssertion ($argspec['url_argname'], $argspec['assertion']);
2773 // "table_colname" is normally used for an override, if it is not
2774 // set, use the URL argument name
2775 $table_colname = array_key_exists ('table_colname', $argspec) ?
2776 $argspec['table_colname'] :
2777 $argspec['url_argname'];
2778 $arg_value = $sic[$argspec['url_argname']];
2779 if
2780 (
2781 ($argspec['assertion'] == 'uint0' and $arg_value == 0)
2782 or ($argspec['assertion'] == 'string0' and $arg_value == '')
2783 )
2784 switch (TRUE)
2785 {
2786 case !array_key_exists ('if_empty', $argspec): // no action requested
2787 break;
2788 case $argspec['if_empty'] == 'NULL':
2789 $arg_value = NULL;
2790 break;
2791 default:
2792 throw new InvalidArgException ('opspec', '(malformed array structure)', '"if_empty" not recognized');
2793 }
2794 $columns[$listname][$table_colname] = $arg_value;
2795 }
cde28cf0
DO
2796 switch ($opspec['action'])
2797 {
2798 case 'INSERT':
09ecff69 2799 $retcode = TRUE === usePreparedInsertBlade ($opspec['table'], $columns['arglist']) ? 48 : 110;
cde28cf0 2800 break;
10005279
DO
2801 case 'DELETE':
2802 $conjunction = array_key_exists ('conjunction', $opspec) ? $opspec['conjunction'] : 'AND';
09ecff69
DO
2803 $retcode = FALSE !== usePreparedDeleteBlade ($opspec['table'], $columns['arglist'], $conjunction) ? 49 : 111;
2804 break;
2805 case 'UPDATE':
2806 usePreparedUpdateBlade
2807 (
2808 $opspec['table'],
2809 $columns['set_arglist'],
2810 $columns['where_arglist'],
2811 array_key_exists ('conjunction', $opspec) ? $opspec['conjunction'] : 'AND'
2812 );
2813 $retcode = 51;
10005279 2814 break;
cde28cf0 2815 default:
548c9349 2816 throw new InvalidArgException ('opspec/action', $opspec['action']);
cde28cf0
DO
2817 }
2818 return buildWideRedirectURL (oneLiner ($retcode));
2819}
2820
e673ee24 2821?>