/*
 * Copyright 1999 Silicon Graphics, Inc. All rights reserved.
 */
#include <lcrash.h>

/*
 * findsym_cmd() -- Run the 'findsym' command.
 */
int
findsym_cmd(command_t *cmd)
{
	int i, symbol_cnt = 0, mode, first_time = TRUE;
	uint64_t value;
	syment_t *sp;


	for (i = 0; i < cmd->nargs; i++) {
		if (first_time ) {
			symbol_banner(cmd->ofp, BANNER|SMAJOR);
			first_time = FALSE;
		}

		if ((sp = kl_lkup_symname(cmd->args[i]))) {
			print_symbol(0, sp, cmd->flags, cmd->ofp);
			symbol_cnt++;
		} else {
			kl_get_value(cmd->args[i], &mode, 0, &value);
			if (KL_ERROR) {
				fprintf(KL_ERRORFP, "Invalid symbol name or "
					"address : %s\n", cmd->args[i]);
				continue;
			}
			if (mode != 2) {
				fprintf(KL_ERRORFP, "Invalid symbol name or "
					"address : %s\n", cmd->args[i]);
				continue;
			}
			if ((sp = kl_lkup_symaddr(value))) {
				if (first_time) {
					symbol_banner(cmd->ofp,
						      (BANNER|SMAJOR));
					first_time = FALSE;
				}
				print_symbol(value, sp, cmd->flags, cmd->ofp);
				symbol_cnt++;
			} else {
				fprintf(KL_ERRORFP, "Invalid symbol name or "
					"address : %s\n", cmd->args[i]);
			}

		}
	}
	if (symbol_cnt) {
		symbol_banner(cmd->ofp, SMAJOR);
		PLURAL("symbol", symbol_cnt, cmd->ofp);
	}
	return(0);
}

#define _FINDSYM_USAGE \
"\n        symname | symaddr [symname | symaddr [...] ]"\
"\n        [-w outfile]"

#define _FINDSYM_HELP \
"Display relevant information for each requested "\
"symbol name and/or symbol address.\n"\
"\nOPTIONS:"\
"\n symname | symaddr [symname | symaddr [...] ]"\
"\n       Search symbol information for given symbol names and addresses."


/*
 * findsym_usage() -- Print the usage string for the 'findsym' command.
 */
void
findsym_usage(command_t *cmd)
{
	CMD_USAGE(cmd, _FINDSYM_USAGE);
}

/*
 * findsym_help() -- Print the help information for the 'findsym' command.
 */
void
findsym_help(command_t *cmd)
{
	CMD_HELP(cmd, _FINDSYM_USAGE, _FINDSYM_HELP);
}

/*
 * findsym_parse() -- Parse the command line arguments for 'findsym'.
 */
int
findsym_parse(command_t *cmd)
{
	if (set_cmd_flags(cmd, (C_TRUE|C_WRITE), 0)) {
		return(1);
	}
	return(0);
}

/*
 * findsym_complete() -- Complete arguments of 'findsym' command.
 */
char *
findsym_complete(command_t *cmd)
{
	char *ret;
	int i;

	/* complete standard options (for example, -w option) arguments
	 */
	if ((ret = complete_standard_options(cmd)) != NOT_COMPLETED) {
		return(ret);
	}
	/* if first character of current word is '-', print usage */
	if ((cmd->args[cmd->nargs - 1] != 0) && 
	    (cmd->args[cmd->nargs - 1][0] == '-')) {
		fprintf(cmd->ofp, "\n");
		findsym_usage(cmd);
		return(DRAW_NEW_ENTIRE_LINE);
	}
	if (cmd->nargs == 1) {
		/* if there is one argument, complete symbol name */
		return(complete_symbol_name(cmd->args[0], 100));
	} else {
		/* if there are two or more arguments */
		for (i = 0; i < cmd->nargs; i++) {
			if (cmd->args[i] && !strcmp(cmd->args[i], "-f")) {
				/* don't complete the word following "-f" */
				return(PRINT_BEEP);
			}
		}
		/* complete symbol name */
		return(complete_symbol_name(cmd->args[cmd->nargs - 1], 100));
	}
}
