main.c

来自「u-boot-1.1.6 for mini2440开发板。 支持网络下载」· C语言 代码 · 共 1,447 行 · 第 1/3 页

C
1,447
字号
	char *p = console_buffer;	unsigned int len=MAX_CMDBUF_SIZE;	int rc;	static int initted = 0;	if (!initted) {		hist_init();		initted = 1;	}	puts (prompt);	rc = cread_line(p, &len);	return rc < 0 ? rc : len;#else	char   *p = console_buffer;	int	n = 0;				/* buffer index		*/	int	plen = 0;			/* prompt length	*/	int	col;				/* output column cnt	*/	char	c;	/* print prompt */	if (prompt) {		plen = strlen (prompt);		puts (prompt);	}	col = plen;	for (;;) {#ifdef CONFIG_BOOT_RETRY_TIME		while (!tstc()) {	/* while no incoming data */			if (retry_time >= 0 && get_ticks() > endtime)				return (-2);	/* timed out */		}#endif		WATCHDOG_RESET();		/* Trigger watchdog, if needed */#ifdef CONFIG_SHOW_ACTIVITY		while (!tstc()) {			extern void show_activity(int arg);			show_activity(0);		}#endif		c = getc();		/*		 * Special character handling		 */		switch (c) {		case '\r':				/* Enter		*/		case '\n':			*p = '\0';			puts ("\r\n");			return (p - console_buffer);		case '\0':				/* nul			*/			continue;		case 0x03:				/* ^C - break		*/			console_buffer[0] = '\0';	/* discard input */			return (-1);		case 0x15:				/* ^U - erase line	*/			while (col > plen) {				puts (erase_seq);				--col;			}			p = console_buffer;			n = 0;			continue;		case 0x17:				/* ^W - erase word 	*/			p=delete_char(console_buffer, p, &col, &n, plen);			while ((n > 0) && (*p != ' ')) {				p=delete_char(console_buffer, p, &col, &n, plen);			}			continue;		case 0x08:				/* ^H  - backspace	*/		case 0x7F:				/* DEL - backspace	*/			p=delete_char(console_buffer, p, &col, &n, plen);			continue;		default:			/*			 * Must be a normal character then			 */			if (n < CFG_CBSIZE-2) {				if (c == '\t') {	/* expand TABs		*/#ifdef CONFIG_AUTO_COMPLETE					/* if auto completion triggered just continue */					*p = '\0';					if (cmd_auto_complete(prompt, console_buffer, &n, &col)) {						p = console_buffer + n;	/* reset */						continue;					}#endif					puts (tab_seq+(col&07));					col += 8 - (col&07);				} else {					++col;		/* echo input		*/					putc (c);				}				*p++ = c;				++n;			} else {			/* Buffer full		*/				putc ('\a');			}		}	}#endif /* CONFIG_CMDLINE_EDITING */}/****************************************************************************/#ifndef CONFIG_CMDLINE_EDITINGstatic char * delete_char (char *buffer, char *p, int *colp, int *np, int plen){	char *s;	if (*np == 0) {		return (p);	}	if (*(--p) == '\t') {			/* will retype the whole line	*/		while (*colp > plen) {			puts (erase_seq);			(*colp)--;		}		for (s=buffer; s<p; ++s) {			if (*s == '\t') {				puts (tab_seq+((*colp) & 07));				*colp += 8 - ((*colp) & 07);			} else {				++(*colp);				putc (*s);			}		}	} else {		puts (erase_seq);		(*colp)--;	}	(*np)--;	return (p);}#endif /* CONFIG_CMDLINE_EDITING *//****************************************************************************/int parse_line (char *line, char *argv[]){	int nargs = 0;#ifdef DEBUG_PARSER	printf ("parse_line: \"%s\"\n", line);#endif	while (nargs < CFG_MAXARGS) {		/* skip any white space */		while ((*line == ' ') || (*line == '\t')) {			++line;		}		if (*line == '\0') {	/* end of line, no more args	*/			argv[nargs] = NULL;#ifdef DEBUG_PARSER		printf ("parse_line: nargs=%d\n", nargs);#endif			return (nargs);		}		argv[nargs++] = line;	/* begin of argument string	*/		/* find end of string */		while (*line && (*line != ' ') && (*line != '\t')) {			++line;		}		if (*line == '\0') {	/* end of line, no more args	*/			argv[nargs] = NULL;#ifdef DEBUG_PARSER		printf ("parse_line: nargs=%d\n", nargs);#endif			return (nargs);		}		*line++ = '\0';		/* terminate current arg	 */	}	printf ("** Too many args (max. %d) **\n", CFG_MAXARGS);#ifdef DEBUG_PARSER	printf ("parse_line: nargs=%d\n", nargs);#endif	return (nargs);}/****************************************************************************/static void process_macros (const char *input, char *output){	char c, prev;	const char *varname_start = NULL;	int inputcnt = strlen (input);	int outputcnt = CFG_CBSIZE;	int state = 0;		/* 0 = waiting for '$'  */	/* 1 = waiting for '(' or '{' */	/* 2 = waiting for ')' or '}' */	/* 3 = waiting for '''  */#ifdef DEBUG_PARSER	char *output_start = output;	printf ("[PROCESS_MACROS] INPUT len %d: \"%s\"\n", strlen (input),		input);#endif	prev = '\0';		/* previous character   */	while (inputcnt && outputcnt) {		c = *input++;		inputcnt--;		if (state != 3) {			/* remove one level of escape characters */			if ((c == '\\') && (prev != '\\')) {				if (inputcnt-- == 0)					break;				prev = c;				c = *input++;			}		}		switch (state) {		case 0:	/* Waiting for (unescaped) $    */			if ((c == '\'') && (prev != '\\')) {				state = 3;				break;			}			if ((c == '$') && (prev != '\\')) {				state++;			} else {				*(output++) = c;				outputcnt--;			}			break;		case 1:	/* Waiting for (        */			if (c == '(' || c == '{') {				state++;				varname_start = input;			} else {				state = 0;				*(output++) = '$';				outputcnt--;				if (outputcnt) {					*(output++) = c;					outputcnt--;				}			}			break;		case 2:	/* Waiting for )        */			if (c == ')' || c == '}') {				int i;				char envname[CFG_CBSIZE], *envval;				int envcnt = input - varname_start - 1;	/* Varname # of chars */				/* Get the varname */				for (i = 0; i < envcnt; i++) {					envname[i] = varname_start[i];				}				envname[i] = 0;				/* Get its value */				envval = getenv (envname);				/* Copy into the line if it exists */				if (envval != NULL)					while ((*envval) && outputcnt) {						*(output++) = *(envval++);						outputcnt--;					}				/* Look for another '$' */				state = 0;			}			break;		case 3:	/* Waiting for '        */			if ((c == '\'') && (prev != '\\')) {				state = 0;			} else {				*(output++) = c;				outputcnt--;			}			break;		}		prev = c;	}	if (outputcnt)		*output = 0;#ifdef DEBUG_PARSER	printf ("[PROCESS_MACROS] OUTPUT len %d: \"%s\"\n",		strlen (output_start), output_start);#endif}/**************************************************************************** * returns: *	1  - command executed, repeatable *	0  - command executed but not repeatable, interrupted commands are *	     always considered not repeatable *	-1 - not executed (unrecognized, bootd recursion or too many args) *           (If cmd is NULL or "" or longer than CFG_CBSIZE-1 it is *           considered unrecognized) * * WARNING: * * We must create a temporary copy of the command since the command we get * may be the result from getenv(), which returns a pointer directly to * the environment data, which may change magicly when the command we run * creates or modifies environment variables (like "bootp" does). */int run_command (const char *cmd, int flag){	cmd_tbl_t *cmdtp;	char cmdbuf[CFG_CBSIZE];	/* working copy of cmd		*/	char *token;			/* start of token in cmdbuf	*/	char *sep;			/* end of token (separator) in cmdbuf */	char finaltoken[CFG_CBSIZE];	char *str = cmdbuf;	char *argv[CFG_MAXARGS + 1];	/* NULL terminated	*/	int argc, inquotes;	int repeatable = 1;	int rc = 0;#ifdef DEBUG_PARSER	printf ("[RUN_COMMAND] cmd[%p]=\"", cmd);	puts (cmd ? cmd : "NULL");	/* use puts - string may be loooong */	puts ("\"\n");#endif	clear_ctrlc();		/* forget any previous Control C */	if (!cmd || !*cmd) {		return -1;	/* empty command */	}	if (strlen(cmd) >= CFG_CBSIZE) {		puts ("## Command too long!\n");		return -1;	}	strcpy (cmdbuf, cmd);	/* Process separators and check for invalid	 * repeatable commands	 */#ifdef DEBUG_PARSER	printf ("[PROCESS_SEPARATORS] %s\n", cmd);#endif	while (*str) {		/*		 * Find separator, or string end		 * Allow simple escape of ';' by writing "\;"		 */		for (inquotes = 0, sep = str; *sep; sep++) {			if ((*sep=='\'') &&			    (*(sep-1) != '\\'))				inquotes=!inquotes;			if (!inquotes &&			    (*sep == ';') &&	/* separator		*/			    ( sep != str) &&	/* past string start	*/			    (*(sep-1) != '\\'))	/* and NOT escaped	*/				break;		}		/*		 * Limit the token to data between separators		 */		token = str;		if (*sep) {			str = sep + 1;	/* start of command for next pass */			*sep = '\0';		}		else			str = sep;	/* no more commands for next pass */#ifdef DEBUG_PARSER		printf ("token: \"%s\"\n", token);#endif		/* find macros in this token and replace them */		process_macros (token, finaltoken);		/* Extract arguments */		if ((argc = parse_line (finaltoken, argv)) == 0) {			rc = -1;	/* no command at all */			continue;		}		/* Look up command in command table */		if ((cmdtp = find_cmd(argv[0])) == NULL) {			printf ("Unknown command '%s' - try 'help'\n", argv[0]);			rc = -1;	/* give up after bad command */			continue;		}		/* found - check max args */		if (argc > cmdtp->maxargs) {			printf ("Usage:\n%s\n", cmdtp->usage);			rc = -1;			continue;		}#if (CONFIG_COMMANDS & CFG_CMD_BOOTD)		/* avoid "bootd" recursion */		if (cmdtp->cmd == do_bootd) {#ifdef DEBUG_PARSER			printf ("[%s]\n", finaltoken);#endif			if (flag & CMD_FLAG_BOOTD) {				puts ("'bootd' recursion detected\n");				rc = -1;				continue;			} else {				flag |= CMD_FLAG_BOOTD;			}		}#endif	/* CFG_CMD_BOOTD */		/* OK - call function to do the command */		if ((cmdtp->cmd) (cmdtp, flag, argc, argv) != 0) {			rc = -1;		}		repeatable &= cmdtp->repeatable;		/* Did the user stop this? */		if (had_ctrlc ())			return 0;	/* if stopped then not repeatable */	}	return rc ? rc : repeatable;}/****************************************************************************/#if (CONFIG_COMMANDS & CFG_CMD_RUN)int do_run (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[]){	int i;	if (argc < 2) {		printf ("Usage:\n%s\n", cmdtp->usage);		return 1;	}	for (i=1; i<argc; ++i) {		char *arg;		if ((arg = getenv (argv[i])) == NULL) {			printf ("## Error: \"%s\" not defined\n", argv[i]);			return 1;		}#ifndef CFG_HUSH_PARSER		if (run_command (arg, flag) == -1)			return 1;#else		if (parse_string_outer(arg,		    FLAG_PARSE_SEMICOLON | FLAG_EXIT_FROM_LOOP) != 0)			return 1;#endif	}	return 0;}#endif	/* CFG_CMD_RUN */

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?