int
main(int argc, char *argv[])
{
	int option_index, rc, fail=0;
	int platform = 0;
	uint64_t dump_tag;

	platform = get_platform();
	switch (platform) {
	case PLATFORM_UNKNOWN:
	case PLATFORM_POWERKVM:
		fprintf(stderr, "%s: is not supported on the %s platform\n",
				argv[0], __power_platform_name(platform));
		return -1;
	}

	for (;;) {
		option_index = 0;
		rc = getopt_long(argc, argv, "hv", long_options,
				&option_index);

		if (rc == -1)
			break;

		switch (rc) {
		case 'h':
			print_usage(argv[0]);
			return 0;
		case 'v':
			flag_v = 1;
			break;
		case '?':
			print_usage(argv[0]);
			return -1;
			break;
		default:
			printf("huh?\n");
			break;
		}
	}

	if (optind < argc) {
		/* Parse ppc64-diag config file */
		rc = diag_cfg(0, &msg);
		if (rc) {
			fprintf(stderr, "Could not parse configuration file "
				"%s\n", config_file);
			return -2;
		}

		while (optind < argc) {
			dump_tag = strtoll(argv[optind++], NULL, 16);
			fail += extract_platform_dump(dump_tag);
		}
	}
	else {
		fprintf(stderr, "No dump tag specified\n");
		print_usage(argv[0]);
		return -1;
	}

	return fail;
}
/**
 * main
 * @brief Parse command line args process database
 *
 * @param argc the number of command-line arguments
 * @param argv array of command-line arguments
 * @return exit status: 0 for normal exit, 1 for usage error, >1 for other error
 */
int
main(int argc, char *argv[])
{
	struct servicelog *slog;
	int rc;
	struct sl_event *event, *events;
	struct sl_repair_action *repair, *repairs;
	struct sl_notify *notify, *notifications;
	int option_index, action=ACTION_UNSPECIFIED;
	int flag_force=0;
	int age = 60;	/* default age for --clean */
	int platform = 0;
	char buf[124];
	char *tmp;
	char *next_char;
	uint32_t num=0, num_repaired=0, num_unrepaired=0, num_info=0, num_ra=0;
	uint32_t span;
	time_t now;

	cmd = argv[0];

	platform = get_platform();
	switch (platform) {
	case PLATFORM_UNKNOWN:
	case PLATFORM_POWERNV:
		fprintf(stderr, "%s: is not supported on the %s platform\n",
					cmd, __power_platform_name(platform));
		exit(1);
	}

	if (argc <= 1) {
		print_usage();
		exit(0);
	}

	for (;;) {
		option_index = 0;
		rc = getopt_long(argc, argv, ARG_LIST, long_options,
				&option_index);

		if (rc == -1)
			break;

		switch (rc) {
		case 's':
			if (action != ACTION_UNSPECIFIED)
				action = ACTION_TOOMANY;
			if (action != ACTION_TOOMANY)
				action = ACTION_STATUS;
			break;
		case 't':
			if (!optarg) {
				fprintf(stderr, "The --truncate option "
					"requires either \"events\" or "
					"\"notify\" as an argument.\n");
				print_usage();
				exit(1);
			}

			if (!strcmp(optarg, "events")) {
				if (action != ACTION_UNSPECIFIED)
					action = ACTION_TOOMANY;
				if (action != ACTION_TOOMANY)
					action = ACTION_TRUNCATE_EVENTS;
			}
			else if (!strcmp(optarg, "notify")) {
				if (action != ACTION_UNSPECIFIED)
					action = ACTION_TOOMANY;
				if (action != ACTION_TOOMANY)
					action = ACTION_TRUNCATE_NOTIFY;
			}
			else {
				fprintf(stderr, "The --truncate option "
					"requires either \"events\" or "
					"\"notify\" as an argument.\n");
				print_usage();
				exit(1);
			}
			break;
		case 'c':
			if (action != ACTION_UNSPECIFIED)
				action = ACTION_TOOMANY;
			if (action != ACTION_TOOMANY)
				action = ACTION_CLEAN;
			break;
		case 'a':
			age = (int)strtoul(optarg, &next_char, 10);
			if (optarg[0] == '\0' || *next_char != '\0' ||
								age < 0) {
				print_usage();
				exit(1);
			}
			break;
		case 'f':
			flag_force = 1;
			break;
		case 'h':	/* help */
			print_usage();
			exit(0);
		case '?':
			print_usage();
			exit(1);
		default:
			printf("Invalid argument: %s\n", optarg);
			print_usage();
			exit(1);
		}
	}

	if (optind < argc) {
		print_usage();
		exit(1);
	}

	/* Command-line validation */
	if (action == ACTION_UNSPECIFIED) {
		fprintf(stderr, "One of the action options is required.\n");
		print_usage();
		exit(1);
	}

	if (action == ACTION_TOOMANY) {
		fprintf(stderr, "Only one of the action options may be "
			"specified.\n");
		print_usage();
		exit(1);
	}


	switch (action) {

	case ACTION_STATUS:
		rc = servicelog_open(&slog, 0);
		if (rc != 0) {
			fprintf(stderr, "%s: Could not open servicelog "
					"database.\n%s\n",
					argv[0], servicelog_error(slog));
			exit(2);
		}

		rc = servicelog_event_query(slog, "", &events);
		if (rc != 0) {
			fprintf(stderr, "%s\n", servicelog_error(slog));
			servicelog_close(slog);
			exit(2);
		}

		for (event = events; event; event = event->next) {
			num++; // total event count
			if (event->serviceable && (event->repair > 0))
				num_repaired++;
			else if (event->serviceable)
				num_unrepaired++;
			else
				num_info++; // informational events
		}

		servicelog_event_free(events);

		// Now need to query repair actions:
		rc = servicelog_repair_query(slog, "", &repairs);
		if (rc != 0) {
			fprintf(stderr, "%s\n", servicelog_error(slog));
			servicelog_close(slog);
			exit(2);
		}

		for (repair = repairs; repair; repair = repair->next)
			num_ra++;
		servicelog_repair_free(repairs);

		servicelog_close(slog);

		printf("%-39s%10u\n", "Logged events:", num);
		printf("    %-35s%10u\n", "unrepaired serviceable events:",
		       num_unrepaired);
		printf("    %-35s%10u\n", "repaired serviceable events:",
		       num_repaired);
		printf("    %-35s%10u\n", "informational events:", num_info);
		printf("    %-35s%10u\n", "repair actions:", num_ra);
		break;


	case ACTION_TRUNCATE_EVENTS:
		if (geteuid() != 0) // Check to see if user is root
		{
			printf("Must be root to truncate the database!\n");
			exit(2);
		}

		num = 0;

		if (!flag_force) {
			printf("Are you certain you wish to delete ALL events "
			       "from the servicelog?\n");
			printf("Enter 'yes' to continue > ");
			tmp = fgets(buf, 80, stdin);
			if (!tmp)
				exit(2);

			if (strcasecmp(buf, "yes\n")) {
				printf("Operation cancelled.\n");
				exit(4);
			}
		}

		rc = servicelog_open(&slog, SL_FLAG_ADMIN);
		if (rc != 0) {
			fprintf(stderr, "%s: Could not open servicelog "
					"database.\n%s\n",
					argv[0], servicelog_error(slog));
			exit(2);
		}
		rc = servicelog_event_query(slog, "", &events);
		if (rc != 0) {
			fprintf(stderr, "%s\n", servicelog_error(slog));
			servicelog_close(slog);
			exit(2);
		}

		for (event = events; event; event = event->next) {
			num++;
			servicelog_event_delete(slog, event->id);
		}

		servicelog_event_free(events);

		// Delete repair actions as well.
		rc = servicelog_repair_query(slog, "", &repairs);
		if (rc != 0) {
			fprintf(stderr, "%s\n", servicelog_error(slog));
			servicelog_close(slog);
			exit(2);
		}

		for (repair = repairs; repair; repair = repair->next) {
			num_ra++;
			servicelog_repair_delete(slog, repair->id);
		}
		servicelog_repair_free(repairs);

		printf("Deleted %u records.\n", num + num_ra);
		servicelog_close(slog);
		break;

	case ACTION_TRUNCATE_NOTIFY:
		if (geteuid() != 0) // Check to see if user is root
		{
			printf("Must be root to truncate the database!\n");
			exit(2);
		}

		num = 0;

		if (!flag_force) {
			printf("Are you certain you wish to delete ALL "
					"notification tools from the servicelog?\n");
			printf("Enter 'yes' to continue > ");
			tmp = fgets(buf, 80, stdin);
			if (!tmp)
				exit(2);

			if (strcasecmp(buf, "yes\n")) {
				printf("Operation cancelled.\n");
				exit(4);
			}
		}

		rc = servicelog_open(&slog, SL_FLAG_ADMIN);
		if (rc != 0) {
			fprintf(stderr, "%s: Could not open servicelog "
					"database.\n%s\n",
					argv[0], servicelog_error(slog));
			exit(2);
		}
		rc = servicelog_notify_query(slog, "", &notifications);
		if (rc != 0) {
			fprintf(stderr, "%s\n", servicelog_error(slog));
			servicelog_close(slog);
			exit(2);
		}

		for (notify = notifications; notify; notify = notify->next) {
			num++;
			servicelog_notify_delete(slog, notify->id);
		}
		servicelog_notify_free(notifications);
		servicelog_close(slog);

		printf("Deleted %u records.\n", num);
		break;

	case ACTION_CLEAN:
		if (geteuid() != 0) { // Check to see if user is root
			printf("Must be root to purge older events "
			       "in the database!\n");
			exit(2);
		}

		if (!flag_force) {
			printf("Are you certain you wish to perform the "
			       "following tasks?\n"
			       " - Delete all repaired serviceable events\n"
			       " - Delete all informational events older than "
			       "%d days\n"
			       " - Delete all repair actions older than "
			       "%d days\n"
			       " - Delete anything older than 1 year\n",
			       age, age);
			printf("Enter 'yes' to continue > ");
			tmp = fgets(buf, 80, stdin);
			if (!tmp)
				exit(2);

			if (strcasecmp(buf, "yes\n")) {
				printf("Operation cancelled.\n");
				break;
			}
		}

		rc = servicelog_open(&slog, 0);
		if (rc != 0) {
			fprintf(stderr, "%s: Could not open servicelog "
					"database.\n%s\n",
					argv[0], servicelog_error(slog));
			exit(2);
		}

		now = time(NULL);
		span = age * SECONDS_IN_DAY;

		rc = servicelog_event_query(slog, "", &events);
		if (rc != 0) {
			fprintf(stderr, "%s\n", servicelog_error(slog));
			servicelog_close(slog);
			exit(2);
		}

		for (event = events; event; event = event->next) {
			if (event->serviceable && event->closed) {
				num_repaired++;
				servicelog_event_delete(slog, event->id);
			}
			else if (!event->serviceable &&
				 (event->time_logged + span) < now) {
				num_info++;
				servicelog_event_delete(slog, event->id);
			}
			else if ((event->time_logged + SECONDS_IN_YEAR) < now) {
				num++;
				servicelog_event_delete(slog, event->id);
			}
		}
		servicelog_event_free(events);

		/* Delete repair actions which are older than age */
		rc = servicelog_repair_query(slog, "", &repairs);
		if (rc != 0) {
			fprintf(stderr, "%s\n", servicelog_error(slog));
			servicelog_close(slog);
			exit(2);
		}
		for (repair = repairs; repair; repair = repair->next) {
			if ((repair->time_logged + span) < now ) {
				num_ra++;
				servicelog_repair_delete(slog, repair->id);
			}
		}
		servicelog_repair_free(repairs);
		servicelog_close(slog);

		printf("Removed %u repaired serviceable events.\n",
		       num_repaired);
		printf("Removed %u informational events older than %d days.\n",
		       num_info, age);
		printf("Removed %u repair actions older than %d days.\n",
		       num_ra, age);
		printf("Removed %u other events older than one year.\n", num);
		break;

	default:
		fprintf(stderr, "Internal error; unknown action %d\n", action);
		exit(3);
	}

	exit(0);
}
int
main(int argc, char *argv[])
{
	int failure = 0, option_index, rc;
	char path[PATH_MAX];
	DIR *edir, *sdir;
	struct dirent *sdirent, *edirent;
	struct dev_vpd *diagnosed = NULL;

	platform = get_platform();
	if (platform != PLATFORM_PSERIES_LPAR) {
		fprintf(stderr, "%s is not supported on the %s platform\n",
				argv[0], __power_platform_name(platform));
		return -1;
	}

	memset(&cmd_opts, 0, sizeof(cmd_opts));

	for (;;) {
		option_index = 0;
		rc = getopt_long(argc, argv, "cf:hlsvV", long_options,
				 &option_index);

		if (rc == -1)
			break;

		switch (rc) {
		case 'c':
			cmd_opts.cmp_prev = 1;
			break;
		case 'f':
			if (cmd_opts.fake_path) {
				fprintf(stderr, "Multiple -f options not "
						"supported.\n");
				return -1;
			}
			cmd_opts.fake_path = optarg;
			break;
		case 'h':
			print_usage(argv[0]);
			return 0;
		case 'l':
			cmd_opts.leds = 1;
			break;
		case 's':
			cmd_opts.serv_event = 1;
			break;
		case 'v':
			cmd_opts.verbose = 1;
			break;
		case 'V':
			printf("%s %s\n", argv[0], VERSION);
			return 0;
		case '?':
			print_usage(argv[0]);
			return -1;
		default:
			/* Shouldn't get here. */
			fprintf(stderr, "huh?\n");
			print_usage(argv[0]);
			return -1;
		}
	}

	if (cmd_opts.cmp_prev && !cmd_opts.serv_event) {
		fprintf(stderr, "No -c option without -s\n");
		return -1;
	}

	if (cmd_opts.leds && !cmd_opts.serv_event) {
		fprintf(stderr, "No -l option without -s\n");
		return -1;
	}

	if ((cmd_opts.serv_event || cmd_opts.leds) && geteuid() != 0) {
		fprintf(stderr, "-s and -l options require superuser "
				"privileges\n");
		return -1;
	}

	if (cmd_opts.fake_path) {
		const char *dot = strrchr(cmd_opts.fake_path, '.');
		if (!dot || strcmp(dot, ".pg2") != 0) {
			fprintf(stderr, "Name of file with fake diagnostic "
					"data must end in '.pg2'.\n");
			return -1;
		}
		if (optind + 1 != argc) {
			fprintf(stderr, "Please specify an sg device with the "
					"-f pathname. It need not be an "
					"enclosure.\n");
			return -1;
		}
		failure += diagnose(argv[optind++], &diagnosed);
	} else if (optind < argc) {
		while (optind < argc)
			failure += diagnose(argv[optind++], &diagnosed);

	} else {
		edir = opendir(SCSI_SES_PATH);
		if (!edir) {
			fprintf(stderr,
				"System does not have SCSI enclosure(s).\n");
			return -1;
		}

		/* loop over all enclosures */
		while ((edirent = readdir(edir)) != NULL) {
			if (!strcmp(edirent->d_name, ".") ||
			    !strcmp(edirent->d_name, ".."))
				continue;

			snprintf(path, PATH_MAX, "%s/%s/device/scsi_generic",
				 SCSI_SES_PATH, edirent->d_name);

			sdir = opendir(path);
			if (!sdir)
				continue;

			while ((sdirent = readdir(sdir)) != NULL) {
				if (!strcmp(sdirent->d_name, ".") ||
				    !strcmp(sdirent->d_name, ".."))
					continue;

				/* run diagnostics */
				failure += diagnose(sdirent->d_name,
						    &diagnosed);
			}
			closedir(sdir);
		} /* outer while loop */
		closedir(edir);
	}

	free(cmd_opts.prev_path);
	free_dev_vpd(diagnosed);

	return failure;
}
/**
 * main  -
 */
int
main(int argc, char **argv)
{
    int	c;
    int	state;
    int	index;
    int	indicator;
    int	rc = 0;
    int	trunc = 0;
    int	truncated = 0;
    int	platform = 0;
    char	temp[LOCATION_LENGTH];
    char	dloc[LOCATION_LENGTH];
    char	*dvalue = NULL;
    char	*lvalue = NULL;
    char	*svalue = NULL;
    char	*othervalue = NULL;
    struct	loc_code *current;
    struct	loc_code *list = NULL;

    platform = get_platform();
    if (platform != PLATFORM_PSERIES_LPAR) {
        fprintf(stderr, "%s is not supported on the %s platform\n",
                argv[0], __power_platform_name(platform));
        return 1;
    }

    opterr = 0;
    while ((c = getopt(argc, argv, CMD_LINE_OPTIONS)) != -1) {
        switch (c) {
        case 'd':
            /* Device name */
            dvalue = optarg;
            break;
        case 'l':
            /* Location code */
            lvalue = optarg;
            break;
        case 's':
            /* Enable/disable */
            svalue = optarg;
            break;
        case '-':
            /* All location code */
            othervalue = optarg;
            break;
        case 't':
            /* truncate location code */
            trunc = 1;
            break;
        case 'V':
            fprintf(stdout, "%s %s\n", argv[0], VERSION);
            fflush(stdout);
            return 0;
        case 'h':
            print_usage(argv[0]);
            return 0;
        case '?':
            if (isprint(optopt))
                fprintf(stderr,
                        "Unrecognized option: -%c\n\n",
                        optopt);
            else
                fprintf(stderr,
                        "Unrecognized option character %x\n\n",
                        optopt);
            print_usage(argv[0]);
            return 1;
        default:
            print_usage(argv[0]);
            return 1;
        }
    }

    /* Option checking */
    for (index = optind; index < argc; index++) {
        fprintf(stderr,
                "Unrecognized argument : %s\n\n", argv[index]);
        print_usage(argv[0]);
        return 1;
    }

    if (dvalue && !strstr(argv[0], CMD_IDENTIFY)) {
        fprintf(stderr, "Unrecognized option: -d\n\n");
        print_usage(argv[0]);
        return 1;
    }

    if (dvalue && lvalue) {
        fprintf(stderr,
                "The -d and -l options cannot be used together.\n\n");
        print_usage(argv[0]);
        return 1;
    }

    if (svalue && strstr(argv[0], CMD_IDENTIFY)) {
        if (!strcmp(svalue, "identify"))
            c = INDICATOR_ON;
        else if (!strcmp(svalue, "normal"))
            c = INDICATOR_OFF;
        else {
            fprintf(stderr,
                    "The -s option must be either "
                    "\"identify\" or \"normal\".\n\n");
            print_usage(argv[0]);
            return 1;
        }
    }

    if (svalue && (strstr(argv[0], CMD_FAULT) ||
                   strstr(argv[0], CMD_ATTN))) {
        if (!strcmp(svalue, "normal"))
            c = INDICATOR_OFF;
        else {
            fprintf(stderr,
                    "The -s option must be \"normal\".\n\n");
            print_usage(argv[0]);
            return 1;
        }
    }

    if (svalue && !(dvalue || lvalue)) {
        if (strstr(argv[0], CMD_IDENTIFY))
            fprintf(stderr,
                    "The -s option requires the -d or -l "
                    "option to also be used.\n\n");
        else
            fprintf(stderr,
                    "The -s option requires the -l "
                    "option to also be used.\n\n");
        print_usage(argv[0]);
        return 1;
    }

    if (svalue && geteuid() != 0) {
        fprintf(stderr,
                "%s: Turning indicator on/off requires "
                "superuser privileges.\n\n", argv[0]);
        return 1;
    }

    if (trunc && !(dvalue || lvalue)) {
        if (strstr(argv[0], CMD_IDENTIFY))
            fprintf(stderr,
                    "The -t option requires the -d or -l "
                    "option to also be used.\n\n");
        else
            fprintf(stderr,
                    "The -t option requires the -l "
                    "option to also be used.\n\n");
        print_usage(argv[0]);
        return 1;
    }

    if (othervalue && strstr(argv[0], CMD_IDENTIFY)) {
        if (!strcmp(othervalue, "all-on"))
            c = INDICATOR_ON;
        else if (!strcmp(othervalue, "all-off"))
            c = INDICATOR_OFF;
        else {
            fprintf(stderr,
                    "Unrecognized option: --%s\n\n", othervalue);
            print_usage(argv[0]);
            return 1;
        }
    }

    if (othervalue && (strstr(argv[0], CMD_ATTN) ||
                       strstr(argv[0], CMD_FAULT))) {
        if (!strcmp(othervalue, "all-off"))
            c = INDICATOR_OFF;
        else {
            fprintf(stderr,
                    "Unrecognized option: --%s\n\n", othervalue);
            print_usage(argv[0]);
            return 1;
        }
    }

    if (othervalue && argc > 2) {
        fprintf(stderr,
                "\"--%s\" cannot be used with any other options.\n\n",
                othervalue);
        print_usage(argv[0]);
        return 1;
    }

    if (strstr(argv[0], CMD_IDENTIFY))
        indicator = IDENT_INDICATOR;
    else if (strstr(argv[0], CMD_FAULT) || strstr(argv[0], CMD_ATTN))
        indicator = ATTN_INDICATOR;
    else
        return 1;

    /* initialize */
    program_name = argv[0];
    lp_error_log_fd = 1; /* log message to stdout */
    rc = init_files();
    if (rc) {
        fprintf(stderr, "Unable to open log file.\n");
        return 1;
    }

    /* Light Path operating mode */
    if (indicator == ATTN_INDICATOR) {
        rc = check_operating_mode();
        if (rc)
            return rc;
    }

    /* get indicator list */
    rc  = get_indicator_list(indicator, &list);
    if (rc)
        goto file_cleanup;

    if (argc == 1) {
        current = list;
        while (current) {
            /* get and print all indicators current state */
            rc = get_indicator_state(indicator, current, &state);
            if (rc) /* failed to get indicator state */
                current->state = -1;
            else
                current->state = state;

            print_indicator_state(current);
            current = current->next;
        }
    }

    /* Turn on/off indicator based on device name */
    if (dvalue) {
        if (get_loc_code_for_dev(dvalue, dloc, LOCATION_LENGTH) != 0) {
            fprintf(stderr,
                    "\"%s\" is not a valid device or "
                    "it does not have location code.\n", dvalue);
            rc = 2;
        } else {
            lvalue = dloc;
            fprintf(stdout, "%s is at location code %s.\n",
                    dvalue, lvalue);
        }
    }

    /* Turn on/off indicator based on location code */
    if (lvalue) {
        strncpy(temp, lvalue, LOCATION_LENGTH);

retry:
        current = get_indicator_for_loc_code(list, lvalue);
        if (!current) {
            if (trunc) {
                if (truncate_loc_code(lvalue)) {
                    truncated = 1;
                    goto retry;
                }
            }
            fprintf(stdout, "There is no %s indicator at location "
                    "code %s.\n", INDICATOR_TYPE(indicator), temp);
            rc = 1;
        } else { /* Found location code */
            if (truncated)
                fprintf(stdout, "Truncated location code : "
                        "%s\n", lvalue);

            if (svalue) {
                rc = get_indicator_state(indicator, current,
                                         &state);

                if (rc || state != c) {
                    rc = set_indicator_state(indicator,
                                             current, c);
                    if (rc)
                        goto indicator_cleanup;
                    indicator_log_state(indicator,
                                        current->code, c);
                }
            }

            rc = get_indicator_state(indicator, current, &state);
            if (!rc) {
                if (dvalue)
                    fprintf(stdout, "%s\t[%s]\n", lvalue,
                            state ? "on" : "off");
                else
                    fprintf(stdout, "%s\n",
                            state ? "on" : "off");
            }
        } /* if-else end */
    } /* lvalue end */

    /* Turn on/off all indicators */
    if (othervalue) {
        current = list;
        while (current) {
            rc = get_indicator_state(indicator, current, &state);
            if (rc) /* failed to get indicator state */
                current->state = -1;
            else
                current->state = state;

            if (state != c) {
                set_indicator_state(indicator, current, c);
                rc = get_indicator_state(indicator, current,
                                         &state);
                if (rc) /* failed to get indicator state */
                    current->state = -1;
                else
                    current->state = state;
            }

            print_indicator_state(current);
            current = current->next;
        }

        /* If enclosure ident indicator is turned ON explicitly,
         * then turning OFF all components ident indicator inside
         * enclosure does not turn OFF enclosure ident indicator.
         */
        if (indicator == IDENT_INDICATOR && c == INDICATOR_OFF)
            set_indicator_state(indicator, &list[0], c);

        indicator_log_write("All %s Indicators : %s",
                            indicator == IDENT_INDICATOR ? "Identify" : "Fault",
                            c == INDICATOR_ON ? "ON" : "OFF");
    }

indicator_cleanup:
    free_indicator_list(list);
file_cleanup:
    close_files();

    return rc;
}