-
void main_loop(void)
-
{
-
#ifndef CONFIG_SYS_HUSH_PARSER
-
static char lastcommand[CONFIG_SYS_CBSIZE] = { 0, };
-
int len;
-
int rc = 1;
-
int flag;
-
#endif
-
#ifdef CONFIG_PREBOOT
-
char *p;
-
#endif
-
-
bootstage_mark_name(BOOTSTAGE_ID_MAIN_LOOP, "main_loop");
-
-
#ifdef CONFIG_MODEM_SUPPORT
-
debug("DEBUG: main_loop: do_mdm_init=%d\n", do_mdm_init);
-
if (do_mdm_init) {
-
char *str = strdup(getenv("mdm_cmd"));
-
setenv("preboot", str); /* set or delete definition */
-
if (str != NULL)
-
free(str);
-
mdm_init(); /* wait for modem connection */
-
}
-
#endif /* CONFIG_MODEM_SUPPORT */
-
-
#ifdef CONFIG_VERSION_VARIABLE
-
{
-
setenv("ver", version_string); /* set version variable */
-
}
-
#endif /* CONFIG_VERSION_VARIABLE */
-
-
#ifdef CONFIG_SYS_HUSH_PARSER
-
u_boot_hush_start();
-
#endif
-
-
#if defined(CONFIG_HUSH_INIT_VAR)
-
hush_init_var();
-
#endif
-
-
#ifdef CONFIG_PREBOOT
-
p = getenv("preboot");
-
if (p != NULL) {
-
# ifdef CONFIG_AUTOBOOT_KEYED
-
int prev = disable_ctrlc(1); /* disable Control C checking */
-
# endif
-
-
run_command_list(p, -1, 0);
-
-
# ifdef CONFIG_AUTOBOOT_KEYED
-
disable_ctrlc(prev); /* restore Control C checking */
-
# endif
-
}
-
#endif /* CONFIG_PREBOOT */
-
-
#if defined(CONFIG_UPDATE_TFTP)
-
update_tftp(0UL);
-
#endif /* CONFIG_UPDATE_TFTP */
-
-
#ifdef CONFIG_BOOTDELAY
-
process_boot_delay();
-
#endif
-
/*
-
* Main Loop for Monitor Command Processing
-
*/
-
#ifdef CONFIG_SYS_HUSH_PARSER
-
parse_file_outer();
-
/* This point is never reached */
-
for (;;);
-
#else
-
for (;;) {
-
#ifdef CONFIG_BOOT_RETRY_TIME
-
if (rc >= 0) {
-
/* Saw enough of a valid command to
-
* restart the timeout.
-
*/
-
reset_cmd_timeout();
-
}
-
#endif
-
len = readline (CONFIG_SYS_PROMPT);//打印提示符,例如SMDKV210#,之后开始从终端读取(接收)一行字符
-
-
flag = 0; /* assume no special flags for now */
-
if (len > 0)
-
strcpy (lastcommand, console_buffer);
-
else if (len == 0)
-
flag |= CMD_FLAG_REPEAT;
-
#ifdef CONFIG_BOOT_RETRY_TIME
-
else if (len == -2) {
-
/* -2 means timed out, retry autoboot
-
*/
-
puts ("\nTimed out waiting for command\n");
-
# ifdef CONFIG_RESET_TO_RETRY
-
/* Reinit board to run initialization code again */
-
do_reset (NULL, 0, 0, NULL);
-
# else
-
return; /* retry autoboot */
-
# endif
-
}
-
#endif
-
-
if (len == -1)
-
puts ("<INTERRUPT>\n");
-
else
-
rc = run_command(lastcommand, flag);
-
-
if (rc <= 0) {
-
/* invalid command or not repeatable, forget it */
-
lastcommand[0] = 0;
-
}
-
}
-
#endif /*CONFIG_SYS_HUSH_PARSER*/
-
}
-
-
/*提示输入,读一行字符,存放到console_buffer字符数组
-
* Prompt for input and read a line.
-
* If CONFIG_BOOT_RETRY_TIME is defined and retry_time >= 0,
-
* time out when time goes past endtime (timebase time in ticks).
-
* Return: number of read characters
-
* -1 if break
-
* -2 if timed out
-
*/
-
int readline (const char *const prompt)
-
{
-
/*
-
* If console_buffer isn't 0-length the user will be prompted to modify
-
* it instead of entering it from scratch as desired.
-
*/
-
console_buffer[0] = '\0';
-
-
return readline_into_buffer(prompt, console_buffer, 0);
-
}
-
/*提示输入,读一行字符,可设定超时功能,Ctrl+C中断
-
* Prompt for input and read a line.
-
* If CONFIG_BOOT_RETRY_TIME is defined and retry_time >= 0,
-
*/
-
-
int readline_into_buffer(const char *const prompt, char *buffer, int timeout)
-
{
-
char *p = buffer;//缓冲区读写指针,缓冲区不包括提示符,而是从提示符之后开始编辑
-
-
//如果有历史功能
-
#ifdef CONFIG_CMDLINE_EDITING
-
unsigned int len = CONFIG_SYS_CBSIZE;
-
int rc;
-
static int initted = 0;
-
-
/*
-
* History uses a global array which is not
-
* writable until after relocation to RAM.
-
* Revert to non-history version if still
-
* running from flash.
-
*/
-
if (gd->flags & GD_FLG_RELOC) {
-
if (!initted) {
-
hist_init();
-
initted = 1;
-
}
-
-
if (prompt)
-
puts (prompt);
-
-
rc = cread_line(prompt, p, &len, timeout);
-
return rc < 0 ? rc : len;
-
-
} else {
-
#endif /* CONFIG_CMDLINE_EDITING */
-
//如果没有历史编辑功能,从这里开始执行
-
char * p_buf = p; //缓冲区首字符指针,即指向console_buffer[0]首字符,
-
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;//列数初始化
-
/*
-
n = plen; //add by richad
-
plen = 0; // To edit promt, plen should be 0, add by richard
-
p += n; //Move pointer to the back of prompt, add by richard
-
*/
-
-
for (;;) {
-
-
WATCHDOG_RESET(); /* Trigger watchdog, if needed */
-
-
c = getc();//输入一个字符
-
-
/*
-
* Special character handling
-
*/
-
switch (c) {
-
case '\r': /* Enter */
-
case '\n':
-
*p = '\0';
-
puts ("\r\n");
-
return p - p_buf;
-
-
case '\0': /* nul */
-
continue;
-
-
case 0x03: /* ^C - break */
-
p_buf[0] = '\0'; /* discard input */ //console_buffer首字符清零,放弃输入
-
return -1;
-
-
case 0x15: /* ^U - erase line */ //NAK,清除一行字符,光标回到起点(不是本行起点,前面还有提示符)
-
while (col > plen) {//删除至提示符
-
puts (erase_seq);//打印退格符,屏幕上的光标会左移
-
--col;//列长度 - 1
-
}
-
p = p_buf;//指针复位,回到缓冲区起点
-
n = 0;
-
continue;
-
-
case 0x17: /* ^W - erase word */
-
p=delete_char(p_buf, p, &col, &n, plen);
-
while ((n > 0) && (*p != ' ')) {
-
p=delete_char(p_buf, p, &col, &n, plen);
-
}
-
continue;
-
-
case 0x08: /* ^H - backspace */
-
case 0x7F: /* DEL - backspace */
-
p=delete_char(p_buf, p, &col, &n, plen);
-
continue;
-
-
default:
-
/*
-
* Must be a normal character then
-
*/
-
if (n < CONFIG_SYS_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 = p_buf + n; /* reset */
-
continue;
-
}
-
#endif
-
puts (tab_seq+(col&07));
-
col += 8 - (col&07);
-
} else {
-
char buf[2];
-
-
/*
-
* Echo input using puts() to force an
-
* LCD flush if we are using an LCD
-
*/
-
++col;
-
buf[0] = c;
-
buf[1] = '\0';
-
puts(buf);
-
}
-
*p++ = c;
-
++n;
-
} else { /* Buffer full */
-
putc ('\a');
-
}
-
}
-
}
-
#ifdef CONFIG_CMDLINE_EDITING
-
}
-
#endif
-
}
-
-
/* 删除一个字符,
-
* *buffer : 缓冲区起点指针
-
* *p : 移动指针
-
* *colp : 当前列计数, 计入prompt,如果prompt为空,colp = 0。colp等于屏幕列坐标
-
* *np : 缓冲区字符计数,为了检查输入字符是否超出上限(512字节)
-
* plen : 命令行提示符长度,修改colp时检查colp是否<plen,防止提示符被误删
-
*/
-
-
p=delete_char(p_buf, p, &col, &n, plen);
-
-
static 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)--;缓冲区计数-1
-
return (p);
-
}
-
-
-
////////////////////////////////////////////////////////////
-
// rc = cread_line(prompt, p, &len, timeout);//读一行字符到缓冲区p, uint len = CONFIG_SYS_CBSIZE;
-
-
/* cread_line: 控制台读一行字符,带历史、编辑功能,
-
* *const promt : 指向提示符的指针,只读
-
* *buf : 缓冲区指针
-
* *len : 控制台字符长度
-
*/
-
-
static int cread_line(const char *const prompt, char *buf, unsigned int *len,
-
int timeout)
-
{
-
unsigned long num = 0;
-
unsigned long eol_num = 0;//行末计数
-
unsigned long wlen;
-
char ichar;
-
int insert = 1;
-
int esc_len = 0;
-
char esc_save[8];
-
int init_len = strlen(buf);//console_buffer字符长度
-
int first = 1;
-
-
if (init_len)//如果console_buffer有字符串,打印其中的字符串并调整*len为总长度,初始值为CONFIG_SYS_CBSIZE = 512,
-
//目的是为了调整num和eol_num
-
cread_add_str(buf, init_len, 1, &num, &eol_num, buf, *len);//增加(打印)字符串buf到控制台缓冲区,并重新调整num和eol_num
-
-
while (1) {
-
-
ichar = getcmd_getch();//等待用户输入一个字符ichar
-
-
if ((ichar == '\n') || (ichar == '\r')) {
-
putc('\n');
-
break;
-
}
-
-
/*
-
* handle standard linux xterm esc sequences for arrow key, etc.
-
*/
-
if (esc_len != 0) {
-
if (esc_len == 1) {
-
if (ichar == '[') {
-
esc_save[esc_len] = ichar;
-
esc_len = 2;
-
} else {
-
cread_add_str(esc_save, esc_len, insert,
-
&num, &eol_num, buf, *len);
-
esc_len = 0;
-
}
-
continue;
-
}
-
-
switch (ichar) {
-
-
case 'D': /* <- key */
-
ichar = CTL_CH('b');
-
esc_len = 0;
-
break;
-
case 'C': /* -> key */
-
ichar = CTL_CH('f');
-
esc_len = 0;
-
break; /* pass off to ^F handler */
-
case 'H': /* Home key */
-
ichar = CTL_CH('a');
-
esc_len = 0;
-
break; /* pass off to ^A handler */
-
case 'A': /* up arrow */
-
ichar = CTL_CH('p');
-
esc_len = 0;
-
break; /* pass off to ^P handler */
-
case 'B': /* down arrow */
-
ichar = CTL_CH('n');
-
esc_len = 0;
-
break; /* pass off to ^N handler */
-
default:
-
esc_save[esc_len++] = ichar;
-
cread_add_str(esc_save, esc_len, insert,
-
&num, &eol_num, buf, *len);
-
esc_len = 0;
-
continue;
-
}
-
}
-
-
switch (ichar) {
-
case 0x1b:
-
if (esc_len == 0) {
-
esc_save[esc_len] = ichar;
-
esc_len = 1;
-
} else {
-
puts("impossible condition #876\n");
-
esc_len = 0;
-
}
-
break;
-
-
case CTL_CH('a'):
-
BEGINNING_OF_LINE();
-
break;
-
case CTL_CH('c'): /* ^C - break */
-
*buf = '\0'; /* discard input */
-
return (-1);
-
case CTL_CH('f'):
-
if (num < eol_num) {
-
getcmd_putch(buf[num]);
-
num++;
-
}
-
break;
-
case CTL_CH('b'):
-
if (num) {
-
getcmd_putch(CTL_BACKSPACE);
-
num--;
-
}
-
break;
-
case CTL_CH('d'):
-
if (num < eol_num) {
-
wlen = eol_num - num - 1;
-
if (wlen) {
-
memmove(&buf[num], &buf[num+1], wlen);
-
putnstr(buf + num, wlen);
-
}
-
-
getcmd_putch(' ');
-
do {
-
getcmd_putch(CTL_BACKSPACE);
-
} while (wlen--);
-
eol_num--;
-
}
-
break;
-
case CTL_CH('k'):
-
ERASE_TO_EOL();
-
break;
-
case CTL_CH('e'):
-
REFRESH_TO_EOL();
-
break;
-
case CTL_CH('o'):
-
insert = !insert;
-
break;
-
case CTL_CH('x'):
-
case CTL_CH('u'):
-
BEGINNING_OF_LINE();
-
ERASE_TO_EOL();
-
break;
-
case DEL:
-
case DEL7:
-
case 8:
-
if (num) {
-
wlen = eol_num - num;
-
num--;
-
memmove(&buf[num], &buf[num+1], wlen);
-
getcmd_putch(CTL_BACKSPACE);
-
putnstr(buf + num, wlen);
-
getcmd_putch(' ');
-
do {
-
getcmd_putch(CTL_BACKSPACE);
-
} while (wlen--);
-
eol_num--;
-
}
-
break;
-
case CTL_CH('p'):
-
case CTL_CH('n'):
-
{
-
char * hline;
-
-
esc_len = 0;
-
-
if (ichar == CTL_CH('p'))
-
hline = hist_prev();
-
else
-
hline = hist_next();
-
-
if (!hline) {
-
getcmd_cbeep();
-
continue;
-
}
-
-
/* nuke the current line */
-
/* first, go home */
-
BEGINNING_OF_LINE();
-
-
/* erase to end of line */
-
ERASE_TO_EOL();
-
-
/* copy new line into place and display */
-
strcpy(buf, hline);
-
eol_num = strlen(buf);
-
REFRESH_TO_EOL();
-
continue;
-
}
-
#ifdef CONFIG_AUTO_COMPLETE
-
case '\t': {
-
int num2, col;
-
-
/* do not autocomplete when in the middle */
-
if (num < eol_num) {
-
getcmd_cbeep();
-
break;
-
}
-
-
buf[num] = '\0';
-
col = strlen(prompt) + eol_num;
-
num2 = num;
-
if (cmd_auto_complete(prompt, buf, &num2, &col)) {
-
col = num2 - num;
-
num += col;
-
eol_num += col;
-
}
-
break;
-
}
-
#endif
-
default:
-
cread_add_char(ichar, insert, &num, &eol_num, buf, *len);
-
break;
-
}
-
}
-
*len = eol_num;
-
buf[eol_num] = '\0'; /* lose the newline */
-
-
if (buf[0] && buf[0] != CREAD_HIST_CHAR)
-
cread_add_to_hist(buf);
-
hist_cur = hist_add_idx;
-
-
return 0;
-
}
-
-
//在当前光标位置增加(打印)字符串*str,调整num、eol_num,和缓冲buf内容
-
static void cread_add_str(char *str, int strsize, int insert, unsigned long *num,
-
unsigned long *eol_num, char *buf, unsigned long len)
-
{
-
while (strsize--) {
-
cread_add_char(*str, insert, num, eol_num, buf, len);
-
str++;
-
}
-
}
-
-
//在当前光标位置增加(打印)一个字符,调整num、eol_num,和缓冲buf内容
-
static void cread_add_char(char ichar, int insert, unsigned long *num,
-
unsigned long *eol_num, char *buf, unsigned long len)
-
{
-
unsigned long wlen;//字长
-
-
/* room ??? */
-
if (insert || *num == *eol_num) {
-
if (*eol_num > len - 1) {
-
getcmd_cbeep();//超出512个字节,报警并返回
-
return;
-
}
-
(*eol_num)++;// 末尾长度+1
-
}
-
-
if (insert) {//以插入方式增加字符
-
wlen = *eol_num - *num;// 1 - 0
-
if (wlen > 1) {
-
memmove(&buf[*num+1], &buf[*num], wlen-1);//以可重叠方式将num位置开始的全部内容向右挪动一个字符,被挪动的字符数为wlen-1即eol_num - num
-
}
-
-
buf[*num] = ichar;//
-
putnstr(buf + *num, wlen);//回显
-
(*num)++;
-
while (--wlen) {
-
getcmd_putch(CTL_BACKSPACE);
-
}
-
} else {//非插入方式,直接覆盖字符,并回显
-
/* echo the character */
-
wlen = 1;
-
buf[*num] = ichar;
-
putnstr(buf + *num, wlen);
-
(*num)++;
-
}
-
}
阅读(2119) | 评论(0) | 转发(0) |