1 /*****************************************************************************\
2 * $Id: ipmipower_prompt.c,v 1.121 2010-08-06 18:38:37 chu11 Exp $
3 *****************************************************************************
4 * Copyright (C) 2007-2015 Lawrence Livermore National Security, LLC.
5 * Copyright (C) 2003-2007 The Regents of the University of California.
6 * Produced at Lawrence Livermore National Laboratory (cf, DISCLAIMER).
7 * Written by Albert Chu <chu11@llnl.gov>
8 * UCRL-CODE-155698
9 *
10 * This file is part of Ipmipower, a remote power control utility.
11 * For details, see http://www.llnl.gov/linux/.
12 *
13 * Ipmipower is free software; you can redistribute it and/or modify
14 * it under the terms of the GNU General Public License as published by the
15 * Free Software Foundation; either version 3 of the License, or (at your
16 * option) any later version.
17 *
18 * Ipmipower is distributed in the hope that it will be useful, but
19 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
20 * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
21 * for more details.
22 *
23 * You should have received a copy of the GNU General Public License along
24 * with Ipmipower. If not, see <http://www.gnu.org/licenses/>.
25 \*****************************************************************************/
26
27 #if HAVE_CONFIG_H
28 #include "config.h"
29 #endif /* HAVE_CONFIG_H */
30
31 #include <stdio.h>
32 #include <stdlib.h>
33 #if STDC_HEADERS
34 #include <string.h>
35 #endif /* STDC_HEADERS */
36 #include <stdint.h>
37 #include <sys/stat.h>
38 #if HAVE_FCNTL_H
39 #include <fcntl.h>
40 #endif /* HAVE_FCNTL_H */
41 #include <assert.h>
42 #if HAVE_UNISTD_H
43 #include <unistd.h>
44 #endif /* HAVE_UNISTD_H */
45 #include <errno.h>
46
47 #include "ipmipower_prompt.h"
48 #include "ipmipower_error.h"
49 #include "ipmipower_connection.h"
50 #include "ipmipower_oem.h"
51 #include "ipmipower_ping.h"
52 #include "ipmipower_powercmd.h"
53 #include "ipmipower_output.h"
54 #include "ipmipower_util.h"
55
56 #include "argv.h"
57
58 #include "freeipmi-portability.h"
59 #include "cbuf.h"
60 #include "fi_hostlist.h"
61 #include "pstdout.h"
62 #include "tool-cmdline-common.h"
63 #include "tool-util-common.h"
64
65 extern cbuf_t ttyout;
66 extern cbuf_t ttyin;
67
68 extern struct ipmipower_arguments cmd_args;
69 extern struct ipmipower_connection *ics;
70
71 extern unsigned int ics_len;
72
73 extern struct oem_power_type_data *oem_power_type_data;
74
75 extern unsigned int output_counts[IPMIPOWER_MSG_TYPE_NUM_ENTRIES];
76
77 /* eliminate
78 *
79 * Note: only for non-interactive mode on the command line. Won't be
80 * anywhere in this file.
81 */
82
83 static void
_cmd_driver_type(char ** argv)84 _cmd_driver_type (char **argv)
85 {
86 assert (argv);
87
88 if (argv[1])
89 {
90 int tmp;
91
92 if ((tmp = parse_outofband_driver_type (argv[1])) < 0)
93 ipmipower_cbuf_printf (ttyout,
94 "invalid driver type '%s' specified\n",
95 argv[1]);
96 else
97 {
98 cmd_args.common_args.driver_type = tmp;
99 ipmipower_cbuf_printf (ttyout,
100 "driver type is now %s\n",
101 argv[1]);
102 }
103 }
104 else
105 ipmipower_cbuf_printf (ttyout,
106 "driver_type must be specified: %s, %s\n",
107 IPMI_PARSE_DEVICE_LAN_STR,
108 IPMI_PARSE_DEVICE_LAN_2_0_STR);
109 }
110
111 static void
_cmd_hostname_clear(void)112 _cmd_hostname_clear (void)
113 {
114 free (cmd_args.common_args.hostname);
115 cmd_args.common_args.hostname = NULL;
116
117 ipmipower_connection_array_destroy (ics, ics_len);
118 ics = NULL;
119 ics_len = 0;
120 }
121
122 static void
_cmd_hostname(char ** argv)123 _cmd_hostname (char **argv)
124 {
125 assert (argv);
126
127 if (!argv[1])
128 {
129 _cmd_hostname_clear ();
130 ipmipower_cbuf_printf (ttyout, "hostname(s) unconfigured\n");
131 }
132 else
133 {
134 struct ipmipower_connection *icsPtr;
135 unsigned int len = 0;
136
137 if (!(icsPtr = ipmipower_connection_array_create (argv[1], &len)))
138 {
139 /* dump error outputs here, most notably invalid hostname output */
140 if (cbuf_read_to_fd (ttyout, STDOUT_FILENO, -1) > 0)
141 return;
142 else
143 ipmipower_cbuf_printf (ttyout,
144 "ipmipower_connection_array_create: %s\n",
145 strerror (errno));
146 return;
147 }
148
149 _cmd_hostname_clear ();
150
151 ics = icsPtr;
152 ics_len = len;
153
154 if (!(cmd_args.common_args.hostname = strdup (argv[1])))
155 {
156 IPMIPOWER_ERROR (("strdup: %s", strerror(errno)));
157 exit (EXIT_FAILURE);
158 }
159
160 ipmipower_ping_force_discovery_sweep ();
161
162 ipmipower_cbuf_printf (ttyout,
163 "hostname: %s\n",
164 cmd_args.common_args.hostname);
165 }
166 }
167
168 static void
_cmd_username(char ** argv)169 _cmd_username (char **argv)
170 {
171 assert (argv);
172
173 if (!argv[1]
174 || (argv[1] && strlen (argv[1]) <= IPMI_MAX_USER_NAME_LENGTH))
175 {
176 free (cmd_args.common_args.username);
177 cmd_args.common_args.username = NULL;
178
179 if (argv[1])
180 {
181 if (!(cmd_args.common_args.username = strdup (argv[1])))
182 {
183 IPMIPOWER_ERROR (("strdup: %s", strerror(errno)));
184 exit (EXIT_FAILURE);
185 }
186 }
187
188 ipmipower_cbuf_printf (ttyout,
189 "username: %s\n",
190 (cmd_args.common_args.username) ? cmd_args.common_args.username : "NULL");
191 }
192 else
193 ipmipower_cbuf_printf (ttyout, "username invalid length\n");
194 }
195
196 static void
_cmd_password(char ** argv)197 _cmd_password (char **argv)
198 {
199 assert (argv);
200
201 if (argv[1] && cmd_args.common_args.authentication_type == IPMI_AUTHENTICATION_TYPE_NONE)
202 ipmipower_cbuf_printf (ttyout,
203 "password cannot be set for authentication_type '%s'\n",
204 IPMI_PARSE_AUTHENTICATION_TYPE_NONE_STR);
205 else if (!argv[1]
206 || (argv[1]
207 && ((cmd_args.common_args.driver_type == IPMI_DEVICE_LAN_2_0
208 && strlen (argv[1]) <= IPMI_2_0_MAX_PASSWORD_LENGTH)
209 || (cmd_args.common_args.driver_type == IPMI_DEVICE_LAN
210 && strlen (argv[1]) <= IPMI_1_5_MAX_PASSWORD_LENGTH))))
211 {
212 free (cmd_args.common_args.password);
213 cmd_args.common_args.password = NULL;
214
215 if (argv[1])
216 {
217 if (!(cmd_args.common_args.password = strdup (argv[1])))
218 {
219 IPMIPOWER_ERROR (("strdup: %s", strerror(errno)));
220 exit (EXIT_FAILURE);
221 }
222 }
223
224 #ifdef NDEBUG
225 ipmipower_cbuf_printf (ttyout, "password changed\n");
226 #else /* !NDEBUG */
227 ipmipower_cbuf_printf (ttyout,
228 "password: %s\n",
229 (cmd_args.common_args.password) ? cmd_args.common_args.password : "NULL");
230 #endif /* !NDEBUG */
231 }
232 else
233 ipmipower_cbuf_printf (ttyout, "password invalid length\n");
234 }
235
236 static void
_cmd_k_g(char ** argv)237 _cmd_k_g (char **argv)
238 {
239 int rv = 0;
240 #ifndef NDEBUG
241 char buf[IPMI_MAX_K_G_LENGTH*2+3];
242 #endif /* !NDEBUG */
243
244 assert (argv);
245
246 if (cmd_args.common_args.driver_type == IPMI_DEVICE_LAN)
247 ipmipower_cbuf_printf (ttyout, "k_g is only used for IPMI 2.0");
248 else
249 {
250 memset (cmd_args.common_args.k_g, '\0', IPMI_MAX_K_G_LENGTH + 1);
251
252 if (argv[1])
253 rv = parse_kg (cmd_args.common_args.k_g, IPMI_MAX_K_G_LENGTH, argv[1]);
254
255 if (rv < 0)
256 ipmipower_cbuf_printf (ttyout, "k_g invalid\n");
257 else
258 {
259 cmd_args.common_args.k_g_len = rv;
260 #ifdef NDEBUG
261 ipmipower_cbuf_printf (ttyout, "k_g changed\n");
262 #else /* !NDEBUG */
263 ipmipower_cbuf_printf (ttyout,
264 "k_g: %s\n",
265 (cmd_args.common_args.k_g_len) ? format_kg (buf,
266 IPMI_MAX_K_G_LENGTH*2+3,
267 cmd_args.common_args.k_g) : "NULL");
268 #endif /* !NDEBUG */
269 }
270 }
271 }
272
273 static void
_cmd_authentication_type(char ** argv)274 _cmd_authentication_type (char **argv)
275 {
276 assert (argv);
277
278 if (argv[1])
279 {
280 int tmp;
281
282 if ((tmp = parse_authentication_type (argv[1])) < 0)
283 ipmipower_cbuf_printf (ttyout,
284 "%s invalid authentication_type\n",
285 argv[1]);
286 else
287 {
288 cmd_args.common_args.authentication_type = tmp;
289 ipmipower_cbuf_printf (ttyout,
290 "authentication type is now %s\n",
291 argv[1]);
292 }
293 }
294 else
295 ipmipower_cbuf_printf (ttyout,
296 "authentication_type must be specified: %s, %s, %s, %s\n",
297 IPMI_PARSE_AUTHENTICATION_TYPE_NONE_STR,
298 IPMI_PARSE_AUTHENTICATION_TYPE_STRAIGHT_PASSWORD_KEY_STR,
299 IPMI_PARSE_AUTHENTICATION_TYPE_MD2_STR,
300 IPMI_PARSE_AUTHENTICATION_TYPE_MD5_STR);
301 }
302
303 static void
_cmd_cipher_suite_id(char ** argv)304 _cmd_cipher_suite_id (char **argv)
305 {
306 assert (argv);
307
308 if (argv[1])
309 {
310 char *endptr;
311 int tmp;
312
313 errno = 0;
314 tmp = strtol (argv[1], &endptr, 10);
315 if (errno
316 || endptr[0] != '\0'
317 || tmp < IPMI_CIPHER_SUITE_ID_MIN
318 || tmp > IPMI_CIPHER_SUITE_ID_MAX)
319 ipmipower_cbuf_printf (ttyout,
320 "%s invalid cipher suite id\n",
321 argv[1]);
322 else if (!IPMI_CIPHER_SUITE_ID_SUPPORTED (tmp))
323 ipmipower_cbuf_printf (ttyout,
324 "%s unsupported cipher suite id\n",
325 argv[1]);
326 else
327 {
328 cmd_args.common_args.cipher_suite_id = tmp;
329 ipmipower_cbuf_printf (ttyout,
330 "cipher suite id is now %s\n",
331 argv[1]);
332 }
333 }
334 else
335 ipmipower_cbuf_printf (ttyout,
336 "cipher_suite_id must be specified: 0, 1, 2, 3, 6, 7, 8, 11, 12\n");
337 }
338
339 static void
_cmd_privilege_level(char ** argv)340 _cmd_privilege_level (char **argv)
341 {
342 assert (argv);
343
344 if (argv[1])
345 {
346 int tmp;
347
348 if ((tmp = parse_privilege_level (argv[1])) < 0)
349 ipmipower_cbuf_printf (ttyout,
350 "%s invalid privilege_level\n",
351 argv[1]);
352 else
353 {
354 cmd_args.common_args.authentication_type = tmp;
355 ipmipower_cbuf_printf (ttyout,
356 "privilege_level type is now %s\n",
357 argv[1]);
358 }
359 }
360 else
361 ipmipower_cbuf_printf (ttyout,
362 "privilege must be specified: %s, %s, %s\n",
363 IPMI_PARSE_PRIVILEGE_LEVEL_USER_STR,
364 IPMI_PARSE_PRIVILEGE_LEVEL_OPERATOR_STR,
365 IPMI_PARSE_PRIVILEGE_LEVEL_ADMIN_STR);
366 }
367
368 static void
_cmd_workaround_flags(char ** argv)369 _cmd_workaround_flags (char **argv)
370 {
371 assert (argv);
372
373 if (argv[1])
374 {
375 unsigned int outofband_flags, outofband_2_0_flags;
376
377 if (parse_workaround_flags_tool (argv[1],
378 &outofband_flags,
379 &outofband_2_0_flags,
380 NULL,
381 NULL,
382 NULL) < 0)
383 ipmipower_cbuf_printf (ttyout,
384 "%s invalid workaround flags specified\n",
385 argv[1]);
386 else
387 {
388 cmd_args.common_args.workaround_flags_outofband = outofband_flags;
389 cmd_args.common_args.workaround_flags_outofband_2_0 = outofband_2_0_flags;
390 ipmipower_cbuf_printf (ttyout,
391 "workaround flags are now %s\n",
392 argv[1]);
393 }
394 }
395 else
396 ipmipower_cbuf_printf (ttyout,
397 "workaround_flags must be specified: %s,%s,%s,%s,%s,%s,%s,%s,%s,%s,%s,%s,%s,%s\n",
398 IPMI_PARSE_WORKAROUND_FLAGS_NONE_STR,
399 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_AUTHENTICATION_CAPABILITIES_STR,
400 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_NO_CHECKSUM_CHECK_STR,
401 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_ACCEPT_SESSION_ID_ZERO_STR,
402 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_FORCE_PERMSG_AUTHENTICATION_STR,
403 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_CHECK_UNEXPECTED_AUTHCODE_STR,
404 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_BIG_ENDIAN_SEQUENCE_NUMBER_STR,
405 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_NO_AUTH_CODE_CHECK_STR,
406 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_2_0_INTEL_2_0_SESSION_STR,
407 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_2_0_SUPERMICRO_2_0_SESSION_STR,
408 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_2_0_SUN_2_0_SESSION_STR,
409 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_2_0_OPEN_SESSION_PRIVILEGE_STR,
410 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_2_0_NON_EMPTY_INTEGRITY_CHECK_VALUE_STR,
411 IPMI_PARSE_SECTION_SPECIFIC_WORKAROUND_FLAGS_IPMIPING_STR);
412 }
413
414 static void
_cmd_power_all_nodes(ipmipower_power_cmd_t cmd)415 _cmd_power_all_nodes (ipmipower_power_cmd_t cmd)
416 {
417 struct ipmipower_connection_extra_arg *eanode;
418 unsigned int nodes_queued = 0;
419 int i;
420
421 assert (IPMIPOWER_POWER_CMD_VALID (cmd));
422
423 memset (output_counts, '\0', sizeof (output_counts));
424
425 for (i = 0; i < ics_len; i++)
426 {
427 if (cmd_args.ping_interval
428 && ics[i].discover_state == IPMIPOWER_DISCOVER_STATE_UNDISCOVERED)
429 ipmipower_output (IPMIPOWER_MSG_TYPE_NOTDISCOVERED, ics[i].hostname, NULL);
430 else if (cmd_args.ping_interval
431 && cmd_args.ping_packet_count
432 && cmd_args.ping_percent
433 && ics[i].discover_state == IPMIPOWER_DISCOVER_STATE_BADCONNECTION)
434 ipmipower_output (IPMIPOWER_MSG_TYPE_BADCONNECTION, ics[i].hostname, NULL);
435 else
436 {
437 if (cmd_args.oem_power_type != IPMIPOWER_OEM_POWER_TYPE_NONE)
438 {
439 eanode = ics[i].extra_args;
440 while (eanode)
441 {
442 if (ipmipower_oem_power_cmd_check_extra_arg (eanode->extra_arg,
443 NULL,
444 0) <= 0)
445 ipmipower_output (IPMIPOWER_MSG_TYPE_INVALID_ARGUMENT_FOR_OEM_EXTENSION,
446 ics[i].hostname,
447 eanode->extra_arg);
448 else
449 {
450 ipmipower_connection_clear (&ics[i]);
451 ipmipower_powercmd_queue (cmd, &ics[i], eanode->extra_arg);
452 nodes_queued++;
453 }
454 eanode = eanode->next;
455 }
456 }
457 else
458 {
459 ipmipower_connection_clear (&ics[i]);
460 ipmipower_powercmd_queue (cmd, &ics[i], NULL);
461 nodes_queued++;
462 }
463 }
464 }
465
466 /* Special corner case when no nodes are discovered */
467 if (!nodes_queued)
468 ipmipower_output_finish ();
469 }
470
471 static void
_cmd_power_specific_nodes(char ** argv,ipmipower_power_cmd_t cmd)472 _cmd_power_specific_nodes (char **argv, ipmipower_power_cmd_t cmd)
473 {
474 fi_hostlist_t h = NULL;
475 fi_hostlist_iterator_t hitr = NULL;
476 fi_hostlist_t h2 = NULL;
477 fi_hostlist_iterator_t h2itr = NULL;
478 char *hstr = NULL;
479 char *h2str = NULL;
480
481 assert (argv);
482 assert (IPMIPOWER_POWER_CMD_VALID (cmd));
483 assert (IPMIPOWER_OEM_POWER_TYPE_VALID (cmd_args.oem_power_type));
484
485 if (!(h = fi_hostlist_create (argv[1])))
486 {
487 ipmipower_cbuf_printf (ttyout, "invalid hostname(s) specified\n");
488 goto cleanup;
489 }
490
491 if (!(hitr = fi_hostlist_iterator_create (h)))
492 {
493 IPMIPOWER_ERROR (("fi_hostlist_iterator_create: %s", strerror (errno)));
494 exit (EXIT_FAILURE);
495 }
496
497 memset (output_counts, '\0', sizeof (output_counts));
498
499 while ((hstr = fi_hostlist_next (hitr)))
500 {
501 /* achu: The double fi_hostlist_create is to handle the corner case
502 * of someone inputting.
503 *
504 * foohost[1-3]+[1-3]
505 *
506 * We need to double fi_hostlist to get all the hosts and extra
507 * args.
508 *
509 * Under most scenarios, this is just inefficient code. But we
510 * feel the performance hit isn't egregious. In addition, the
511 * code logic is simpler to do it this way then have a whole
512 * bunch of wacky if-check scenarios to make it more efficient.
513 * We'll revisit as necessary in the future.
514 */
515
516 if (!(h2 = fi_hostlist_create (hstr)))
517 {
518 ipmipower_cbuf_printf (ttyout, "invalid hostname(s) specified\n");
519 goto cleanup;
520 }
521
522 fi_hostlist_uniq (h2);
523
524 if (!(h2itr = fi_hostlist_iterator_create (h2)))
525 {
526 IPMIPOWER_ERROR (("fi_hostlist_iterator_create: %s", strerror (errno)));
527 exit (EXIT_FAILURE);
528 }
529
530 while ((h2str = fi_hostlist_next (h2itr)))
531 {
532 char *h2str_extra_arg = NULL;
533 int i;
534
535 if (cmd_args.oem_power_type != IPMIPOWER_OEM_POWER_TYPE_NONE)
536 {
537 char *ptr;
538
539 if ((ptr = strchr (h2str, '+')))
540 {
541 *ptr = '\0';
542 ptr++;
543
544 if (!(h2str_extra_arg = strdup (ptr)))
545 {
546 IPMIPOWER_ERROR (("strdup: %s", strerror(errno)));
547 exit (EXIT_FAILURE);
548 }
549 }
550 }
551
552 i = ipmipower_connection_hostname_index (ics, ics_len, h2str);
553
554 if (i < 0)
555 ipmipower_output (IPMIPOWER_MSG_TYPE_UNCONFIGURED_HOSTNAME, h2str, NULL);
556 else if (cmd_args.ping_interval
557 && ics[i].discover_state == IPMIPOWER_DISCOVER_STATE_UNDISCOVERED)
558 ipmipower_output (IPMIPOWER_MSG_TYPE_NOTDISCOVERED, ics[i].hostname, NULL);
559 else if (cmd_args.ping_interval
560 && cmd_args.ping_packet_count
561 && cmd_args.ping_percent
562 && ics[i].discover_state == IPMIPOWER_DISCOVER_STATE_BADCONNECTION)
563 ipmipower_output (IPMIPOWER_MSG_TYPE_BADCONNECTION, ics[i].hostname, NULL);
564 else
565 {
566 if (cmd_args.oem_power_type != IPMIPOWER_OEM_POWER_TYPE_NONE)
567 {
568 if (ipmipower_oem_power_cmd_check_extra_arg (h2str_extra_arg,
569 NULL,
570 0) <= 0)
571 {
572 ipmipower_output (IPMIPOWER_MSG_TYPE_INVALID_ARGUMENT_FOR_OEM_EXTENSION,
573 ics[i].hostname,
574 h2str_extra_arg);
575 goto end_inner_loop;
576 }
577 ipmipower_connection_clear (&ics[i]);
578 ipmipower_powercmd_queue (cmd, &ics[i], h2str_extra_arg);
579 }
580 else
581 {
582 ipmipower_connection_clear (&ics[i]);
583 ipmipower_powercmd_queue (cmd, &ics[i], NULL);
584 }
585 }
586
587 end_inner_loop:
588 free (h2str_extra_arg);
589 free (h2str);
590 h2str = NULL;
591 }
592
593 fi_hostlist_iterator_destroy (h2itr);
594 fi_hostlist_destroy (h2);
595 h2itr = NULL;
596 h2 = NULL;
597 }
598
599 cleanup:
600 fi_hostlist_iterator_destroy (h2itr);
601 fi_hostlist_destroy (h2);
602 fi_hostlist_iterator_destroy (hitr);
603 fi_hostlist_destroy (h);
604 free (hstr);
605 free (h2str);
606 }
607
608 static void
_cmd_power(char ** argv,ipmipower_power_cmd_t cmd)609 _cmd_power (char **argv, ipmipower_power_cmd_t cmd)
610 {
611 char errbuf[IPMIPOWER_OUTPUT_BUFLEN + 1];
612
613 assert (argv);
614 assert (IPMIPOWER_POWER_CMD_VALID (cmd));
615 assert (IPMIPOWER_OEM_POWER_TYPE_VALID (cmd_args.oem_power_type));
616
617 if (!cmd_args.common_args.hostname)
618 {
619 ipmipower_cbuf_printf (ttyout, "no hostname(s) configured\n");
620 return;
621 }
622
623 memset (errbuf, '\0', IPMIPOWER_OUTPUT_BUFLEN + 1);
624 if (cmd_args.oem_power_type == IPMIPOWER_OEM_POWER_TYPE_NONE)
625 {
626 if (ipmipower_power_cmd_check_privilege (cmd,
627 errbuf,
628 IPMIPOWER_OUTPUT_BUFLEN) <= 0)
629 {
630 ipmipower_cbuf_printf (ttyout, "%s\n", errbuf);
631 return;
632 }
633 }
634 else
635 {
636 if (ipmipower_oem_power_cmd_check_support_and_privilege (cmd,
637 errbuf,
638 IPMIPOWER_OUTPUT_BUFLEN) <= 0)
639 {
640 ipmipower_cbuf_printf (ttyout, "%s\n", errbuf);
641 return;
642 }
643 }
644
645 /* all nodes */
646 if (!argv[1])
647 _cmd_power_all_nodes (cmd);
648 else
649 _cmd_power_specific_nodes (argv, cmd);
650 }
651
652 static void
_cmd_help(void)653 _cmd_help (void)
654 {
655 ipmipower_cbuf_printf (ttyout,
656 "driver-type IPMIDRIVER - Specify the ipmi driver to use.\n"
657 "hostname [IPMIHOST] - Specify a new set of hosts. No input to unconfigure all hosts.\n"
658 "username [USERNAME] - Specify a new username. No input for null username.\n"
659 "password [PASSWORD] - Specify a new password. No input for null password.\n"
660 "k_g [K_G] - Specify a new K_g BMC Key. No input for null key.\n"
661 "session-timeout MILLISECONDS - Specify a new session timeout length.\n"
662 "retransmission-timeout MILLISECONDS - Specify a new retransmission timeout length.\n"
663 "authentication-type AUTHENTICATION-TYPE - Specify the authentication type to use.\n"
664 "cipher-suite-id CIPHER-SUITE-ID - Specify the cipher suite id to use.\n"
665 "privilege-level PRIVILEGE-LEVEL - Specify the privilege level to use.\n"
666 "workaround-flags WORKAROUNDS - Specify workaround flags.\n"
667 "debug [on|off] - Toggle debug to stderr.\n");
668 #ifndef NDEBUG
669 ipmipower_cbuf_printf (ttyout,
670 "rmcpdump [on|off] - Toggle RMCP dump output.\n");
671 #endif /* NDEBUG */
672 ipmipower_cbuf_printf (ttyout,
673 "on [IPMIHOST(s)] - Turn on all configured hosts or specified hosts.\n"
674 "off [IPMIHOST(s)] - Turn off all configured hosts or specified hosts.\n"
675 "cycle [IPMIHOST(s)] - Power cycle all configured hosts or specified hosts.\n"
676 "reset [IPMIHOST(s)] - Reset all configured hosts or specified hosts.\n"
677 "stat [IPMIHOST(s)] - Query power status for all configured hosts or specified hosts.\n"
678 "pulse [IPMIHOST(s)] - Pulse diagnostic interrupt all configured hosts or specified hosts.\n"
679 "soft [IPMIHOST(s)] - Initiate a soft-shutdown for all configured hosts or specified hosts.\n"
680 "identify-on [IPMIHOST(s)] - Turn on physical system identification.\n"
681 "identify-off [IPMIHOST(s)] - Turn off physical system identification.\n"
682 "identify-status [IPMIHOST(s)] - Query physical system identification status.\n"
683 "on-if-off [on|off] - Toggle on-if-off functionality.\n"
684 "wait-until-on [on|off] - Toggle wait-until-on functionality.\n"
685 "wait-until-off [on|off] - Toggle wait-until-off functionality.\n"
686 "retransmission-wait-timeout MILLISECONDS - Specify a new retransmission timeout length.\n"
687 "retransmission-backoff-count COUNT - Specify a new retransmission backoff count.\n"
688 "ping-interval MILLISECONDS - Specify a new ping interval length.\n"
689 "ping-timeout MILLISECONDS - Specify a new ping timeout length.\n"
690 "ping-packet-count COUNT - Specify a new ping packet count.\n"
691 "ping-percent COUNT - Specify a new ping percent number.\n"
692 "ping-consec-count COUNT - Specify a new ping consec count.\n"
693 "buffer-output [on|off] - Toggle buffer-output functionality.\n"
694 "consolidate-output [on|off] - Toggle consolidate-output functionality.\n"
695 "fanout COUNT - Specify a fanout.\n"
696 "always-prefix [on|off] - Toggle always-prefix functionality.\n"
697 "help - Output help menu.\n"
698 "version - Output version.\n"
699 "config - Output current configuration.\n"
700 "quit - Quit program.\n");
701 }
702
703 static void
_cmd_version(void)704 _cmd_version (void)
705 {
706 ipmipower_cbuf_printf (ttyout, "ipmipower %s\n", VERSION);
707 }
708
709 static void
_workarounds_strcat(char * strbuf,unsigned int bitmask,unsigned int mask,const char * str,int * is_first)710 _workarounds_strcat (char *strbuf,
711 unsigned int bitmask,
712 unsigned int mask,
713 const char *str,
714 int *is_first)
715 {
716 assert (strbuf && str && is_first);
717
718 if (bitmask & mask)
719 {
720 if ((*is_first))
721 strcat (strbuf, ",");
722 strcat (strbuf, str);
723 (*is_first)++;
724 }
725 }
726
727 static void
_cmd_debug(char ** argv)728 _cmd_debug (char **argv)
729 {
730 assert (argv);
731
732 if (!argv[1])
733 cmd_args.common_args.debug = !cmd_args.common_args.debug;
734 else
735 {
736 if (!strcasecmp (argv[1], "on"))
737 cmd_args.common_args.debug = 1;
738 else if (!strcasecmp (argv[1], "off"))
739 cmd_args.common_args.debug = 0;
740 else
741 {
742 ipmipower_cbuf_printf (ttyout, "invalid parameter\n");
743 return;
744 }
745 }
746 ipmipower_cbuf_printf (ttyout,
747 "debugging is now %s\n", (cmd_args.common_args.debug) ? "on" : "off");
748 }
749
750 static void
_cmd_config(void)751 _cmd_config (void)
752 {
753 #ifndef NDEBUG
754 char kgbuf[IPMI_MAX_K_G_LENGTH*2+3];
755 #endif /* NDEBUG */
756 char strbuf[IPMIPOWER_OUTPUT_BUFLEN];
757 char *str;
758 int is_first = 0;
759
760 str = "";
761 if (cmd_args.common_args.driver_type == IPMI_DEVICE_LAN)
762 str = IPMI_PARSE_DEVICE_LAN_STR;
763 else if (cmd_args.common_args.driver_type == IPMI_DEVICE_LAN_2_0)
764 str = IPMI_PARSE_DEVICE_LAN_2_0_STR;
765
766 ipmipower_cbuf_printf (ttyout,
767 "Driver_Type: %s\n",
768 str);
769
770 if (cmd_args.common_args.hostname)
771 {
772 #ifndef NDEBUG
773 int i;
774 fi_hostlist_t discovered = NULL;
775 fi_hostlist_t undiscovered = NULL;
776 fi_hostlist_t badconnection = NULL;
777 char buf[IPMIPOWER_OUTPUT_BUFLEN];
778 int rv;
779 #endif /* NDEBUG */
780
781 ipmipower_cbuf_printf (ttyout,
782 "Hostname: %s\n",
783 cmd_args.common_args.hostname);
784
785 #ifndef NDEBUG
786 if (!(discovered = fi_hostlist_create (NULL)))
787 goto cleanup;
788 if (!(undiscovered = fi_hostlist_create (NULL)))
789 goto cleanup;
790 if (!(badconnection = fi_hostlist_create (NULL)))
791 goto cleanup;
792
793 for (i = 0; i < ics_len; i++)
794 {
795 if (ics[i].discover_state == IPMIPOWER_DISCOVER_STATE_DISCOVERED)
796 rv = fi_hostlist_push_host (discovered, ics[i].hostname);
797 else if (ics[i].discover_state == IPMIPOWER_DISCOVER_STATE_UNDISCOVERED)
798 rv = fi_hostlist_push_host (undiscovered, ics[i].hostname);
799 else
800 rv = fi_hostlist_push_host (badconnection, ics[i].hostname);
801
802 if (!rv)
803 goto cleanup;
804 }
805
806 fi_hostlist_sort (discovered);
807 fi_hostlist_sort (undiscovered);
808 fi_hostlist_sort (badconnection);
809
810 if ((rv = fi_hostlist_ranged_string (discovered, IPMIPOWER_OUTPUT_BUFLEN, buf)) < 0)
811 {
812 IPMIPOWER_ERROR (("fi_hostlist_ranged_string: %s", strerror (errno)));
813 exit (EXIT_FAILURE);
814 }
815
816 if (rv > 0)
817 ipmipower_cbuf_printf (ttyout,
818 "Discovered: %s\n",
819 buf);
820
821 if ((rv = fi_hostlist_ranged_string (undiscovered, IPMIPOWER_OUTPUT_BUFLEN, buf)) < 0)
822 {
823 IPMIPOWER_ERROR (("fi_hostlist_ranged_string: %s", strerror (errno)));
824 exit (EXIT_FAILURE);
825 }
826
827 if (rv > 0)
828 ipmipower_cbuf_printf (ttyout,
829 "Undiscovered: %s\n",
830 buf);
831
832 if ((rv = fi_hostlist_ranged_string (badconnection, IPMIPOWER_OUTPUT_BUFLEN, buf)) < 0)
833 {
834 IPMIPOWER_ERROR (("fi_hostlist_ranged_string: %s", strerror (errno)));
835 exit (EXIT_FAILURE);
836 }
837
838 if (rv > 0)
839 ipmipower_cbuf_printf (ttyout,
840 "BadConnection: %s\n",
841 buf);
842
843 cleanup:
844 fi_hostlist_destroy (discovered);
845 fi_hostlist_destroy (undiscovered);
846 fi_hostlist_destroy (badconnection);
847 #endif /* NDEBUG */
848 }
849 else
850 ipmipower_cbuf_printf (ttyout,
851 "Hostname: NONE\n");
852
853 ipmipower_cbuf_printf (ttyout,
854 "Username: %s\n",
855 (cmd_args.common_args.username) ? cmd_args.common_args.username : "NULL");
856
857 #ifndef NDEBUG
858 ipmipower_cbuf_printf (ttyout,
859 "Password: %s\n",
860 (cmd_args.common_args.password) ? cmd_args.common_args.password : "NULL");
861 ipmipower_cbuf_printf (ttyout,
862 "K_g: %s\n",
863 (cmd_args.common_args.k_g_len) ?
864 format_kg (kgbuf, IPMI_MAX_K_G_LENGTH*2+3, cmd_args.common_args.k_g) : "NULL");
865 #else /* !NDEBUG */
866 ipmipower_cbuf_printf (ttyout,
867 "Password: *****\n");
868 ipmipower_cbuf_printf (ttyout,
869 "K_g: *****\n");
870 #endif /* !NDEBUG */
871
872 ipmipower_cbuf_printf (ttyout,
873 "Session Timeout: %u ms\n",
874 cmd_args.common_args.session_timeout);
875 ipmipower_cbuf_printf (ttyout,
876 "Retransmission Timeout: %u ms\n",
877 cmd_args.common_args.retransmission_timeout);
878
879 str = "";
880 if (cmd_args.common_args.authentication_type == IPMI_AUTHENTICATION_TYPE_NONE)
881 str = IPMI_PARSE_AUTHENTICATION_TYPE_NONE_STR;
882 else if (cmd_args.common_args.authentication_type == IPMI_AUTHENTICATION_TYPE_MD2)
883 str = IPMI_PARSE_AUTHENTICATION_TYPE_MD2_STR;
884 else if (cmd_args.common_args.authentication_type == IPMI_AUTHENTICATION_TYPE_MD5)
885 str = IPMI_PARSE_AUTHENTICATION_TYPE_MD5_STR;
886 else if (cmd_args.common_args.authentication_type == IPMI_AUTHENTICATION_TYPE_STRAIGHT_PASSWORD_KEY)
887 str = IPMI_PARSE_AUTHENTICATION_TYPE_STRAIGHT_PASSWORD_KEY_STR;
888
889 ipmipower_cbuf_printf (ttyout,
890 "Authentication_Type: %s\n",
891 str);
892
893 str = "";
894 if (cmd_args.common_args.cipher_suite_id == 0)
895 str = "0";
896 else if (cmd_args.common_args.cipher_suite_id == 1)
897 str = "1";
898 else if (cmd_args.common_args.cipher_suite_id == 2)
899 str = "2";
900 else if (cmd_args.common_args.cipher_suite_id == 3)
901 str = "3";
902 else if (cmd_args.common_args.cipher_suite_id == 6)
903 str = "6";
904 else if (cmd_args.common_args.cipher_suite_id == 7)
905 str = "7";
906 else if (cmd_args.common_args.cipher_suite_id == 8)
907 str = "8";
908 else if (cmd_args.common_args.cipher_suite_id == 11)
909 str = "11";
910 else if (cmd_args.common_args.cipher_suite_id == 12)
911 str = "12";
912
913 ipmipower_cbuf_printf (ttyout,
914 "Cipher Suite Id: %s\n",
915 str);
916
917 str = "";
918 if (cmd_args.common_args.privilege_level == IPMI_PRIVILEGE_LEVEL_USER)
919 str = IPMI_PARSE_PRIVILEGE_LEVEL_USER_STR;
920 else if (cmd_args.common_args.privilege_level == IPMI_PRIVILEGE_LEVEL_OPERATOR)
921 str = IPMI_PARSE_PRIVILEGE_LEVEL_OPERATOR_STR;
922 else if (cmd_args.common_args.privilege_level == IPMI_PRIVILEGE_LEVEL_ADMIN)
923 str = IPMI_PARSE_PRIVILEGE_LEVEL_ADMIN_STR;
924
925 ipmipower_cbuf_printf (ttyout,
926 "Privilege_Level: %s\n",
927 str);
928
929 memset (strbuf, '\0', IPMIPOWER_OUTPUT_BUFLEN);
930 is_first = 0;
931 _workarounds_strcat (strbuf,
932 cmd_args.common_args.workaround_flags_outofband,
933 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_AUTHENTICATION_CAPABILITIES,
934 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_AUTHENTICATION_CAPABILITIES_STR,
935 &is_first);
936 _workarounds_strcat (strbuf,
937 cmd_args.common_args.workaround_flags_outofband,
938 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_ACCEPT_SESSION_ID_ZERO,
939 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_ACCEPT_SESSION_ID_ZERO_STR,
940 &is_first);
941 _workarounds_strcat (strbuf,
942 cmd_args.common_args.workaround_flags_outofband,
943 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_FORCE_PERMSG_AUTHENTICATION,
944 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_FORCE_PERMSG_AUTHENTICATION_STR,
945 &is_first);
946 _workarounds_strcat (strbuf,
947 cmd_args.common_args.workaround_flags_outofband,
948 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_CHECK_UNEXPECTED_AUTHCODE,
949 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_CHECK_UNEXPECTED_AUTHCODE_STR,
950 &is_first);
951 _workarounds_strcat (strbuf,
952 cmd_args.common_args.workaround_flags_outofband,
953 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_BIG_ENDIAN_SEQUENCE_NUMBER,
954 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_BIG_ENDIAN_SEQUENCE_NUMBER_STR,
955 &is_first);
956 _workarounds_strcat (strbuf,
957 cmd_args.common_args.workaround_flags_outofband,
958 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_NO_AUTH_CODE_CHECK,
959 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_NO_AUTH_CODE_CHECK_STR,
960 &is_first);
961 _workarounds_strcat (strbuf,
962 cmd_args.common_args.workaround_flags_outofband,
963 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_NO_CHECKSUM_CHECK,
964 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_NO_CHECKSUM_CHECK_STR,
965 &is_first);
966 /* This is a duplicate of the IPMI 1.5 version */
967 #if 0
968 _workarounds_strcat (strbuf,
969 cmd_args.common_args.workaround_flags_outofband_2_0,
970 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_2_0_AUTHENTICATION_CAPABILITIES,
971 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_2_0_AUTHENTICATION_CAPABILITIES_STR,
972 &is_first);
973 #endif
974 _workarounds_strcat (strbuf,
975 cmd_args.common_args.workaround_flags_outofband_2_0,
976 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_2_0_INTEL_2_0_SESSION,
977 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_2_0_INTEL_2_0_SESSION_STR,
978 &is_first);
979 _workarounds_strcat (strbuf,
980 cmd_args.common_args.workaround_flags_outofband_2_0,
981 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_2_0_SUPERMICRO_2_0_SESSION,
982 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_2_0_SUPERMICRO_2_0_SESSION_STR,
983 &is_first);
984 _workarounds_strcat (strbuf,
985 cmd_args.common_args.workaround_flags_outofband_2_0,
986 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_2_0_SUN_2_0_SESSION,
987 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_2_0_SUN_2_0_SESSION_STR,
988 &is_first);
989 _workarounds_strcat (strbuf,
990 cmd_args.common_args.workaround_flags_outofband_2_0,
991 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_2_0_OPEN_SESSION_PRIVILEGE,
992 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_2_0_OPEN_SESSION_PRIVILEGE_STR,
993 &is_first);
994 _workarounds_strcat (strbuf,
995 cmd_args.common_args.workaround_flags_outofband_2_0,
996 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_2_0_NON_EMPTY_INTEGRITY_CHECK_VALUE,
997 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_2_0_NON_EMPTY_INTEGRITY_CHECK_VALUE_STR,
998 &is_first);
999 /* This is a duplicate of the IPMI 1.5 version */
1000 #if 0
1001 _workarounds_strcat (strbuf,
1002 cmd_args.common_args.workaround_flags_outofband_2_0,
1003 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_2_0_NO_CHECKSUM_CHECK,
1004 IPMI_PARSE_WORKAROUND_FLAGS_OUTOFBAND_2_0_NO_CHECKSUM_CHECK_STR,
1005 &is_first);
1006 #endif
1007 _workarounds_strcat (strbuf,
1008 cmd_args.common_args.workaround_flags_outofband_2_0,
1009 IPMI_PARSE_SECTION_SPECIFIC_WORKAROUND_FLAGS_IPMIPING,
1010 IPMI_PARSE_SECTION_SPECIFIC_WORKAROUND_FLAGS_IPMIPING_STR,
1011 &is_first);
1012
1013 ipmipower_cbuf_printf (ttyout,
1014 "WorkaroundFlags: %s\n",
1015 strbuf);
1016
1017 ipmipower_cbuf_printf (ttyout,
1018 "Debug: %s\n",
1019 cmd_args.common_args.debug ? "on" : "off");
1020
1021 #ifndef NDEBUG
1022 ipmipower_cbuf_printf (ttyout,
1023 "Rmcpdump: %s\n",
1024 (cmd_args.rmcpdump) ? "on" : "off");
1025 #endif /* NDEBUG */
1026
1027 ipmipower_cbuf_printf (ttyout,
1028 "On-If-Off: %s\n",
1029 (cmd_args.on_if_off) ? "enabled" : "disabled");
1030 ipmipower_cbuf_printf (ttyout,
1031 "Wait-Until-On: %s\n",
1032 (cmd_args.wait_until_on) ? "enabled" : "disabled");
1033 ipmipower_cbuf_printf (ttyout,
1034 "Wait-Until-Off: %s\n",
1035 (cmd_args.wait_until_off) ? "enabled" : "disabled");
1036 ipmipower_cbuf_printf (ttyout,
1037 "Retransmission Wait Timeout: %u ms\n",
1038 cmd_args.retransmission_wait_timeout);
1039 ipmipower_cbuf_printf (ttyout,
1040 "Retransmission Backoff Count: %u\n",
1041 cmd_args.retransmission_backoff_count);
1042 ipmipower_cbuf_printf (ttyout,
1043 "Ping Interval: %u ms\n",
1044 cmd_args.ping_interval);
1045 ipmipower_cbuf_printf (ttyout,
1046 "Ping Timeout: %u ms\n",
1047 cmd_args.ping_timeout);
1048 ipmipower_cbuf_printf (ttyout,
1049 "Ping Packet Count: %u\n",
1050 cmd_args.ping_packet_count);
1051 ipmipower_cbuf_printf (ttyout,
1052 "Ping Percent: %u percent\n",
1053 cmd_args.ping_percent);
1054 ipmipower_cbuf_printf (ttyout,
1055 "Ping Consec Count: %u\n",
1056 cmd_args.ping_consec_count);
1057
1058 ipmipower_cbuf_printf (ttyout,
1059 "Buffer-Output: %s\n",
1060 (cmd_args.common_args.buffer_output) ? "enabled" : "disabled");
1061 ipmipower_cbuf_printf (ttyout,
1062 "Consolidate-Output: %s\n",
1063 (cmd_args.common_args.consolidate_output) ? "enabled" : "disabled");
1064 ipmipower_cbuf_printf (ttyout,
1065 "Fanout: %u\n",
1066 cmd_args.common_args.fanout);
1067 ipmipower_cbuf_printf (ttyout,
1068 "Always-Prefix: %s\n",
1069 (cmd_args.common_args.always_prefix) ? "enabled" : "disabled");
1070 }
1071
1072 static void
_cmd_set_unsigned_int(char ** argv,unsigned int * value,const char * str,int allow_zero)1073 _cmd_set_unsigned_int (char **argv,
1074 unsigned int *value,
1075 const char *str,
1076 int allow_zero)
1077 {
1078 assert (argv && value && str);
1079
1080 if (!argv[1])
1081 ipmipower_cbuf_printf (ttyout,
1082 "%s not specified\n",
1083 str);
1084 else
1085 {
1086 char *endptr;
1087 unsigned int temp;
1088
1089 errno = 0;
1090 temp = strtoul (argv[1], &endptr, 10);
1091 if (errno
1092 || endptr[0] != '\0')
1093 ipmipower_cbuf_printf (ttyout,
1094 "invalid %s input\n",
1095 str);
1096 else if (allow_zero && !temp)
1097 {
1098 *value = temp;
1099 ipmipower_cbuf_printf (ttyout,
1100 "%s is now %d\n",
1101 str,
1102 *value);
1103 }
1104 else
1105 ipmipower_cbuf_printf (ttyout,
1106 "invalid %s input\n",
1107 str);
1108 }
1109 }
1110
1111 static void
_cmd_set_unsigned_int_ranged(char ** argv,unsigned int * value,const char * str,int allow_zero,int min,int max)1112 _cmd_set_unsigned_int_ranged (char **argv,
1113 unsigned int *value,
1114 const char *str,
1115 int allow_zero,
1116 int min,
1117 int max)
1118 {
1119 assert (argv && value && str);
1120
1121 if (!argv[1])
1122 ipmipower_cbuf_printf (ttyout,
1123 "%s not specified\n",
1124 str);
1125 else
1126 {
1127 char *endptr;
1128 int temp;
1129
1130 errno = 0;
1131 temp = strtol (argv[1], &endptr, 10);
1132 if (errno
1133 || endptr[0] != '\0')
1134 ipmipower_cbuf_printf (ttyout,
1135 "invalid %s input\n",
1136 str);
1137 else if ((allow_zero
1138 && !temp)
1139 || (temp <= max
1140 && temp >= min))
1141 {
1142 *value = temp;
1143 ipmipower_cbuf_printf (ttyout,
1144 "%s is now %d\n",
1145 str,
1146 *value);
1147 }
1148 else
1149 ipmipower_cbuf_printf (ttyout,
1150 "invalid %s input, range is %d <=> %d\n",
1151 str,
1152 min,
1153 max);
1154 }
1155 }
1156
1157 static void
_cmd_set_flag(char ** argv,int * flag,const char * str)1158 _cmd_set_flag (char **argv, int *flag, const char *str)
1159 {
1160 assert (argv && flag && str);
1161
1162 if (!argv[1])
1163 *flag = !(*flag);
1164 else
1165 {
1166 if (!strcasecmp (argv[1], "on"))
1167 *flag = 1;
1168 else if (!strcasecmp (argv[1], "off"))
1169 *flag = 0;
1170 else
1171 {
1172 ipmipower_cbuf_printf (ttyout, "invalid parameter\n");
1173 return;
1174 }
1175 }
1176 ipmipower_cbuf_printf (ttyout,
1177 "%s is now %s\n",
1178 str,
1179 (*flag) ? "on" : "off");
1180 }
1181
1182 /* _readcmd
1183 * - Read a command line from the tty and return it in buf.
1184 * If no commands are available, return a null-terminated empty string.
1185 */
1186 static void
_readcmd(char * buf,int buflen)1187 _readcmd (char *buf, int buflen)
1188 {
1189 int dropped, bytes_peeked, len = 0;
1190
1191 buf[0] = '\0';
1192 if ((bytes_peeked = cbuf_peek (ttyin, buf, buflen)) < 0)
1193 {
1194 IPMIPOWER_ERROR (("cbuf_peek: %s", strerror (errno)));
1195 exit (EXIT_FAILURE);
1196 }
1197
1198 if (!bytes_peeked)
1199 return;
1200
1201 for (len = 0; len < bytes_peeked; len++)
1202 {
1203 if (buf[len] == '\n')
1204 {
1205 buf[len+1] = '\0';
1206 break;
1207 }
1208 }
1209
1210 if (len == bytes_peeked)
1211 return;
1212
1213 len++;
1214
1215 if ((dropped = cbuf_drop (ttyin, len)) != len)
1216 IPMIPOWER_DEBUG (("cbuf_drop returned %d != %d)", dropped, len));
1217 }
1218
1219 int
ipmipower_prompt_process_cmdline(void)1220 ipmipower_prompt_process_cmdline (void)
1221 {
1222 static int need_prompt = 1;
1223 char *buf;
1224 int quit = 0;
1225
1226 if (!(buf = (char *)malloc (IPMIPOWER_MAX_TTY_BUF)))
1227 {
1228 IPMIPOWER_ERROR (("malloc: %s", strerror(errno)));
1229 exit (EXIT_FAILURE);
1230 }
1231
1232 do
1233 {
1234 if (ipmipower_powercmd_pending ())
1235 break;
1236 if (need_prompt)
1237 {
1238 ipmipower_cbuf_printf (ttyout, "ipmipower> ");
1239 need_prompt = 0;
1240 }
1241 buf[0] = '\0';
1242 _readcmd (buf, IPMIPOWER_MAX_TTY_BUF);
1243 if (strlen (buf) > 0)
1244 {
1245 char **argv = argv_create (buf, "");
1246 int i;
1247
1248 if (argv[0])
1249 {
1250 /* support "ipmi_version" and "ipmi-version" for backwards compatability */
1251 if (!strcmp (argv[0], "driver-type")
1252 || !strcmp (argv[0], "ipmi_version")
1253 || !strcmp (argv[0], "ipmi-version"))
1254 _cmd_driver_type (argv);
1255 /* support hostnames (plural) for backwards compatability */
1256 else if (!strcmp (argv[0], "hostnames")
1257 || !strcmp (argv[0], "hostname"))
1258 _cmd_hostname (argv);
1259 else if (!strcmp (argv[0], "username"))
1260 _cmd_username (argv);
1261 else if (!strcmp (argv[0], "password"))
1262 _cmd_password (argv);
1263 else if (!strcmp (argv[0], "k_g"))
1264 _cmd_k_g (argv);
1265 /* support "timeout" for backwards compatability */
1266 else if (!strcmp (argv[0], "timeout")
1267 || !strcmp (argv[0], "session-timeout"))
1268 _cmd_set_unsigned_int (argv,
1269 &cmd_args.common_args.session_timeout,
1270 "timeout",
1271 0);
1272 /* support "retry-timeout" for backwards compatability */
1273 else if (!strcmp (argv[0], "retry-timeout")
1274 || !strcmp (argv[0], "retransmission-timeout"))
1275 _cmd_set_unsigned_int_ranged (argv,
1276 &cmd_args.common_args.retransmission_timeout,
1277 "retransmission-timeout",
1278 0,
1279 1,
1280 cmd_args.common_args.session_timeout);
1281 /* support underscored version for backwards compatability */
1282 else if (!strcmp (argv[0], "authentication_type")
1283 || !strcmp (argv[0], "authentication-type"))
1284 _cmd_authentication_type (argv);
1285 /* support underscored version for backwards compatability */
1286 else if (!strcmp (argv[0], "cipher_suite_id")
1287 || !strcmp (argv[0], "cipher-suite-id"))
1288 _cmd_cipher_suite_id (argv);
1289 /* support "privilege" command for backwards compatability */
1290 else if (!strcmp (argv[0], "privilege")
1291 || !strcmp (argv[0], "privilege-level"))
1292 _cmd_privilege_level (argv);
1293 else if (!strcmp (argv[0], "workaround-flags"))
1294 _cmd_workaround_flags (argv);
1295 else if (!strcmp (argv[0], "debug"))
1296 _cmd_debug (argv);
1297 #ifndef NDEBUG
1298 else if (!strcmp (argv[0], "rmcpdump"))
1299 _cmd_set_flag (argv,
1300 &cmd_args.rmcpdump,
1301 "rmcp dump");
1302 #endif /* NDEBUG */
1303 else if (!strcmp (argv[0], "happyeaster"))
1304 ipmipower_cbuf_printf (ttyout, "by Albert Chu <chu11@llnl.gov>\n");
1305 else if (!strcmp (argv[0], "on"))
1306 _cmd_power (argv, IPMIPOWER_POWER_CMD_POWER_ON);
1307 else if (!strcmp (argv[0], "off"))
1308 _cmd_power (argv, IPMIPOWER_POWER_CMD_POWER_OFF);
1309 else if (!strcmp (argv[0], "cycle"))
1310 _cmd_power (argv, IPMIPOWER_POWER_CMD_POWER_CYCLE);
1311 else if (!strcmp (argv[0], "reset"))
1312 _cmd_power (argv, IPMIPOWER_POWER_CMD_POWER_RESET);
1313 else if (!strcmp (argv[0], "stat"))
1314 _cmd_power (argv, IPMIPOWER_POWER_CMD_POWER_STATUS);
1315 else if (!strcmp (argv[0], "pulse"))
1316 _cmd_power (argv, IPMIPOWER_POWER_CMD_PULSE_DIAGNOSTIC_INTERRUPT);
1317 else if (!strcmp (argv[0], "soft"))
1318 _cmd_power (argv, IPMIPOWER_POWER_CMD_SOFT_SHUTDOWN_OS);
1319 else if (!strcmp (argv[0], "identify-on"))
1320 _cmd_power (argv, IPMIPOWER_POWER_CMD_IDENTIFY_ON);
1321 else if (!strcmp (argv[0], "identify-off"))
1322 _cmd_power (argv, IPMIPOWER_POWER_CMD_IDENTIFY_OFF);
1323 else if (!strcmp (argv[0], "identify-status"))
1324 _cmd_power (argv, IPMIPOWER_POWER_CMD_IDENTIFY_STATUS);
1325 else if (!strcmp (argv[0], "on-if-off"))
1326 _cmd_set_flag (argv,
1327 &cmd_args.on_if_off,
1328 "on-if-off");
1329 else if (!strcmp (argv[0], "wait-until-on"))
1330 _cmd_set_flag (argv,
1331 &cmd_args.wait_until_on,
1332 "wait-until-on");
1333 else if (!strcmp (argv[0], "wait-until-off"))
1334 _cmd_set_flag (argv,
1335 &cmd_args.wait_until_off,
1336 "wait-until-off");
1337 /* support "retry-wait-timeout" for backwards compatability */
1338 else if (!strcmp (argv[0], "retry-wait-timeout")
1339 || !strcmp (argv[0], "retransmission-wait-timeout"))
1340 _cmd_set_unsigned_int_ranged (argv,
1341 &cmd_args.retransmission_wait_timeout,
1342 "retransmission-wait-timeout",
1343 0,
1344 1,
1345 cmd_args.common_args.session_timeout);
1346 /* support "retry-backoff-count" for backwards compatability */
1347 else if (!strcmp (argv[0], "retry-backoff-count")
1348 || !strcmp (argv[0], "retransmission-backoff-count"))
1349 _cmd_set_unsigned_int (argv,
1350 &cmd_args.retransmission_backoff_count,
1351 "retransmission-backoff-count",
1352 0);
1353 else if (!strcmp (argv[0], "ping-interval"))
1354 _cmd_set_unsigned_int_ranged (argv,
1355 &cmd_args.ping_interval,
1356 "ping-interval",
1357 1,
1358 0,
1359 cmd_args.ping_timeout);
1360 else if (!strcmp (argv[0], "ping-timeout"))
1361 _cmd_set_unsigned_int (argv,
1362 &cmd_args.ping_timeout,
1363 "ping-timeout",
1364 1);
1365 else if (!strcmp (argv[0], "ping-packet-count"))
1366 _cmd_set_unsigned_int (argv,
1367 &cmd_args.ping_packet_count,
1368 "ping-packet-count",
1369 1);
1370 else if (!strcmp (argv[0], "ping-percent"))
1371 _cmd_set_unsigned_int (argv,
1372 &cmd_args.ping_percent,
1373 "ping-percent",
1374 1);
1375 else if (!strcmp (argv[0], "ping-consec-count"))
1376 _cmd_set_unsigned_int_ranged (argv,
1377 &cmd_args.ping_consec_count,
1378 "ping-consec-count",
1379 1,
1380 0,
1381 cmd_args.ping_packet_count);
1382 else if (!strcmp (argv[0], "buffer-output"))
1383 _cmd_set_flag (argv,
1384 &cmd_args.common_args.buffer_output,
1385 "buffer-output");
1386 else if (!strcmp (argv[0], "consolidate-output"))
1387 _cmd_set_flag (argv,
1388 &cmd_args.common_args.consolidate_output,
1389 "consolidate-output");
1390 else if (!strcmp (argv[0], "always-prefix"))
1391 _cmd_set_flag (argv,
1392 &cmd_args.common_args.always_prefix,
1393 "always-prefix");
1394 else if (!strcmp (argv[0], "fanout"))
1395 _cmd_set_unsigned_int_ranged (argv,
1396 &cmd_args.common_args.fanout,
1397 "fanout",
1398 1,
1399 PSTDOUT_FANOUT_MIN,
1400 PSTDOUT_FANOUT_MAX);
1401 else if (!strcmp (argv[0], "help")
1402 || !strcmp (argv[0], "?")
1403 || !strcmp (argv[0], "advanced") /* legacy */
1404 || !strcmp (argv[0], "network")) /* legacy */
1405 _cmd_help ();
1406 else if (!strcmp (argv[0], "version"))
1407 _cmd_version ();
1408 else if (!strcmp (argv[0], "config"))
1409 _cmd_config ();
1410 else if (!strcmp (argv[0], "quit"))
1411 quit = 1;
1412 else
1413 ipmipower_cbuf_printf (ttyout, "unknown command - type \"help\"\n");
1414 }
1415 need_prompt = 1;
1416
1417 /* Clear out argv data for generic security purposes since
1418 * usernames or passwords could be stored here. argv_create
1419 * guarantees a null terminated pointer, so this loop is
1420 * safe
1421 */
1422 i = 0;
1423 while (argv[i])
1424 {
1425 memset (argv[i], '\0', strlen (argv[i]));
1426 i++;
1427 }
1428
1429 argv_destroy (argv);
1430 }
1431 } while (!quit && strlen (buf) > 0);
1432 free (buf);
1433
1434 return (!quit);
1435 }
1436