Changeset 1193 for trunk/src/target/u-boot/patches/boot-menu.patch
- Timestamp:
- 03/01/07 18:03:44 (6 years ago)
- File:
-
- 1 edited
-
trunk/src/target/u-boot/patches/boot-menu.patch (modified) (18 diffs)
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/target/u-boot/patches/boot-menu.patch
r1133 r1193 7 7 neo1973_on_key_pressed 8 8 board/neo1973/neo1973.h: added function prototypes 9 u-boot/board/neo1973/neo1973.c: removed setting of "nobootdelay"10 9 u-boot/board/neo1973/neo1973.c (board_late_init): enter the boot menu when 11 10 "AUX" was pressed at least half the time 12 11 u-boot/board/neo1973/neo1973.c (board_late_init): minor code cleanup 12 u-boot/common/console.c, include/console.h: added "console_poll_hook" to be 13 called when waiting for console in put in "getc" and "tstc" 13 14 14 15 - Werner Almesberger <werner@openmoko.org> … … 18 19 --- /dev/null 19 20 +++ u-boot/board/neo1973/bootmenu.c 20 @@ -0,0 +1, 187@@21 @@ -0,0 +1,335 @@ 21 22 +/* 22 23 + * bootmenu.c - Boot menu … … 43 44 + 44 45 +#include <common.h> 46 +#include <devices.h> 47 +#include <console.h> 45 48 +#include <environment.h> 46 49 + … … 54 57 + 55 58 +#define DEBOUNCE_LOOPS 1000 /* wild guess */ 56 +#define BOOT_MENU_TIMEOUT 60 /* 60 second */ 59 + 60 +/* 61 + * MIN_BOOT_MENU_TIMEOUT ensures that users can't by accident set the timeout 62 + * unusably short. 63 + */ 64 +#define MIN_BOOT_MENU_TIMEOUT 10 /* 10 seconds */ 65 +#define BOOT_MENU_TIMEOUT 60 /* 60 seconds */ 57 66 +#define AFTER_COMMAND_WAIT 3 /* wait (2,3] after running commands */ 58 67 +#define MAX_MENU_ITEMS 10 /* cut off after that many */ … … 62 71 + 63 72 + 73 +/* 74 + * The menu options are indexed as follows: 75 + * 76 + * 0 Hard-coded "Boot" 77 + * n User-provided options 78 + * options+1 Hard-coded "Factory reset" 79 + * 80 + * "options" is the number of user-provided options. They are stored in 81 + * environment variables names "menu_N", starting with 1. 82 + * 83 + * Because there can be * holes in the sequence of "menu_N" variables, we use 84 + * map[] to map the option number to the number in the variable name. The 85 + * first variable goes into map[1], etc., so that, if we start with menu_1 and 86 + * have no holes, map[i] == i for 1 <= i <= options. 87 + */ 88 + 89 +static int map[MAX_MENU_ITEMS]; 64 90 +static int options = 0; 65 91 +static int width = sizeof(FACTORY_TXT)-1; 66 + 67 + 68 +static int debounce(int (*fn)(void)) 92 +static int boot_menu_timeout; 93 + 94 +static device_t *bm_con; 95 + 96 + 97 +static void bm_printf(const char *fmt, ...) 98 +{ 99 + va_list args; 100 + char printbuffer[CFG_PBSIZE]; 101 + 102 + va_start(args, fmt); 103 + vsprintf(printbuffer, fmt, args); 104 + va_end(args); 105 + 106 + bm_con->puts(printbuffer); 107 +} 108 + 109 + 110 +static int debounce(int (*fn)(void), int last) 69 111 +{ 70 112 + int on, i; … … 72 114 +again: 73 115 + on = fn(); 74 + for (i = DEBOUNCE_LOOPS; i; i--) 75 + if (on != fn()) 76 + goto again; 116 + if (on != last) 117 + for (i = DEBOUNCE_LOOPS; i; i--) 118 + if (on != fn()) 119 + goto again; 77 120 + return on; 78 121 +} … … 83 126 + char name[] = "menu_XX"; 84 127 + 85 + sprintf(name+5,"%d", n);128 + sprintf(name+5,"%d",map[n]); 86 129 + return getenv(name); 87 130 +} … … 94 137 + 95 138 + if (!n) { 96 + printf(" %-*s ", width, BOOT_TXT);139 + bm_printf(" %-*s ", width, BOOT_TXT); 97 140 + return; 98 141 + } 99 142 + if (n == options+1) { 100 + printf(" %-*s ", width, FACTORY_TXT);143 + bm_printf(" %-*s ", width, FACTORY_TXT); 101 144 + return; 102 145 + } … … 110 153 + if (len > width) 111 154 + width = len; 112 + printf(" %-*s ", width, s);155 + bm_printf(" %-*s ", width, s); 113 156 + if (colon) 114 157 + *colon = ':'; … … 118 161 +static void print_option(int n, int reverse) 119 162 +{ 120 + printf(ANSI_GOTOYX, n+4, 1);163 + bm_printf(ANSI_GOTOYX, n+4, 1); 121 164 + if (reverse) 122 + printf(ANSI_REVERSE);165 + bm_printf(ANSI_REVERSE); 123 166 + print_option_n(n); 124 167 + if (reverse) 125 + printf(ANSI_NORMAL);168 + bm_printf(ANSI_NORMAL); 126 169 +} 127 170 + … … 139 182 + 140 183 + 141 +static int do_bootmenu(void) 142 +{ 143 + int aux = 1, on = 1; 144 + int n, seconds = 0; 145 + 146 + printf(ANSI_CLEAR ANSI_GOTOYX "*** BOOT MENU ***\n\n", 2, 1); 184 +static int get_var_positive_int(char *var, int default_value) 185 +{ 186 + const char *s; 187 + char *end; 188 + int n; 189 + 190 + s = getenv(var); 191 + if (!s) 192 + return default_value; 193 + n = simple_strtoul(s, &end, 0); 194 + if (!*s || *end || n < 1) 195 + return default_value; 196 + return n; 197 +} 198 + 199 + 200 +static void init_bootmenu(void) 201 +{ 202 + int n; 203 + 204 + bm_printf(ANSI_CLEAR ANSI_GOTOYX "*** BOOT MENU ***\n\n", 2, 1); 205 + options = 0; 206 + 207 + /* hard-coded first option */ 147 208 + print_option(0, 1); 148 + while (options < MAX_MENU_ITEMS && option_command(options+1)) 149 + print_option(++options, 0); 209 + map[0] = 0; 210 + 211 + /* user-provided options */ 212 + for (n = 1; n != MAX_MENU_ITEMS+1; n++) { 213 + map[options+1] = n; 214 + if (option_command(options+1)) { 215 + options++; 216 + print_option(options, 0); 217 + } 218 + } 219 + 220 + /* hard-coded last option */ 150 221 + print_option(options+1, 0); 151 + printf("\n\nPress [AUX] to select, [POWER] to execute.\n"); 152 + 153 + n = 0; 154 + while (1) { 222 + map[options+1] = options+1; 223 + 224 + bm_printf("\n\nPress [AUX] to select, [POWER] to execute.\n"); 225 + 226 + boot_menu_timeout = get_var_positive_int("boot_menu_timeout", 227 + BOOT_MENU_TIMEOUT); 228 + if (boot_menu_timeout < MIN_BOOT_MENU_TIMEOUT) 229 + boot_menu_timeout = MIN_BOOT_MENU_TIMEOUT; 230 +} 231 + 232 + 233 +static void redirect_console(int grab) 234 +{ 235 + static device_t *orig_stdout, *orig_stderr; 236 + 237 + if (grab) { 238 + orig_stdout = stdio_devices[stdout]; 239 + orig_stderr = stdio_devices[stderr]; 240 + stdio_devices[stdout] = bm_con; 241 + stdio_devices[stderr] = bm_con; 242 + } 243 + else { 244 + /* 245 + * Make this conditional, because the command may also change 246 + * the console. 247 + */ 248 + if (stdio_devices[stdout] == bm_con) 249 + stdio_devices[stdout] = orig_stdout; 250 + if (stdio_devices[stderr] == bm_con) 251 + stdio_devices[stderr] = orig_stderr; 252 + } 253 +} 254 + 255 + 256 +static void do_option(int option) 257 +{ 258 + int seconds, aux; 259 + 260 + bm_printf(ANSI_CLEAR ANSI_GOTOYX, 1, 1); 261 + redirect_console(1); 262 + if (!option || option == options+1) { 263 + if (option) { 264 + default_env(); 265 + run_command("dynpart", 0); 266 + } 267 + run_command("bootd", 0); 268 + } 269 + else 270 + run_command(option_command(option), 0); 271 + redirect_console(0); 272 + seconds = get_var_positive_int("after_command_wait", 273 + AFTER_COMMAND_WAIT); 274 + if (seconds) 275 + bm_printf("\nPress [AUX] to %s.", 276 + option ? "return to boot menu" : "power off"); 277 + aux = 1; /* require up-down transition */ 278 + while (seconds) { 155 279 + int tmp; 156 280 + 157 + tmp = debounce(neo1973_911_key_pressed); 158 + if (tmp && !aux) { 159 + print_option(n, 0); 160 + n++; 161 + if (n == options+2) 162 + n = 0; 163 + print_option(n, 1); 164 + seconds = 0; 165 + } 281 + tmp = debounce(neo1973_911_key_pressed, aux); 282 + if (tmp && !aux) 283 + break; 166 284 + aux = tmp; 167 + tmp = debounce(neo1973_on_key_pressed);168 + if (tmp && !on)169 + return n;170 + on = tmp;171 285 + if (neo1973_new_second()) 172 + if (++seconds > BOOT_MENU_TIMEOUT) 173 + return -1; 174 + } 286 + seconds--; 287 + } 288 + if (!option) 289 + neo1973_poweroff(); 290 + init_bootmenu(); 291 +} 292 + 293 + 294 +static void bootmenu_hook(int activity) 295 +{ 296 + static int aux = 1, on = 1; 297 + static int option = 0; 298 + static int seconds = 0; 299 + int tmp; 300 + 301 + if (activity) 302 + seconds = 0; 303 + tmp = debounce(neo1973_911_key_pressed, aux); 304 + if (tmp && !aux) { 305 + print_option(option, 0); 306 + option++; 307 + if (option == options+2) 308 + option = 0; 309 + print_option(option, 1); 310 + seconds = 0; 311 + } 312 + aux = tmp; 313 + tmp = debounce(neo1973_on_key_pressed, on); 314 + if (tmp && !on) { 315 + do_option(option); 316 + option = 0; 317 + seconds = 0; 318 + } 319 + on = tmp; 320 + if (neo1973_new_second()) 321 + if (++seconds > boot_menu_timeout) 322 + neo1973_poweroff(); 323 +} 324 + 325 + 326 +static device_t *find_console(const char *name) 327 +{ 328 + int i; 329 + 330 + for (i = 1; i != ListNumItems(devlist); i++) { 331 + device_t *dev = ListGetPtrToItem(devlist, i); 332 + 333 + if (!strcmp(name, dev->name)) 334 + if (dev->flags & DEV_FLAGS_OUTPUT) 335 + return dev; 336 + } 337 + return NULL; 175 338 +} 176 339 + … … 178 341 +void bootmenu(void) 179 342 +{ 343 + bm_con = find_console("vga"); 344 + if (bm_con && bm_con->start && bm_con->start() < 0) 345 + bm_con = NULL; 346 + if (!bm_con) 347 + bm_con = stdio_devices[stdout]; 348 + if (!bm_con) 349 + return; 350 +#if 0 180 351 + console_assign(stdout, "vga"); 181 352 + console_assign(stderr, "vga"); 182 + while (1) { 183 + int n, seconds; 184 + 185 + options = 0; 186 + n = do_bootmenu(); 187 + if (n < 0) 188 + return; 189 + 190 + printf(ANSI_CLEAR ANSI_GOTOYX, 1, 1); 191 + if (!n || n == options+1) { 192 + if (n) { 193 + default_env(); 194 + run_command("dynpart", 0); 195 + } 196 + run_command("bootd", 0); 197 + if (!n) 198 + return; 199 + } 200 + else 201 + run_command(option_command(n), 0); 202 + seconds = AFTER_COMMAND_WAIT; 203 + while (seconds) 204 + if (neo1973_new_second()) 205 + seconds--; 206 + } 353 +#endif 354 + init_bootmenu(); 355 + console_poll_hook = bootmenu_hook; 207 356 +} 208 357 Index: u-boot/board/neo1973/neo1973.c … … 210 359 --- u-boot.orig/board/neo1973/neo1973.c 211 360 +++ u-boot/board/neo1973/neo1973.c 212 @@ -69,7 +69,6 @@ DECLARE_GLOBAL_DATA_PTR; 213 #define U_M_SDIV 0x3 214 215 unsigned int neo1973_wakeup_cause; 216 -extern int nobootdelay; 217 218 static inline void delay (unsigned long loops) 219 { 220 @@ -196,6 +195,7 @@ int board_late_init(void) 361 @@ -196,6 +196,7 @@ int board_late_init(void) 221 362 extern unsigned char booted_from_nand; 222 363 unsigned char tmp; … … 226 367 /* Initialize the Power Management Unit with a safe register set */ 227 368 pcf50606_init(); 228 @@ -219,25 +2 19,18 @@ int board_late_init(void)369 @@ -219,25 +220,18 @@ int board_late_init(void) 229 370 230 371 if (tmp & PCF50606_INT1_ONKEYF) { … … 259 400 goto continue_boot; 260 401 } 261 @@ -262,6 +25 5,11 @@ continue_boot:402 @@ -262,6 +256,11 @@ continue_boot: 262 403 /* switch on the backlight */ 263 404 neo1973_backlight(1); … … 265 406 + if (menu_vote > 0) { 266 407 + bootmenu(); 267 + n eo1973_poweroff();408 + nobootdelay = 1; 268 409 + } 269 410 + … … 271 412 } 272 413 273 @@ -313,6 +31 1,16 @@ void neo1973_vibrator(int on)414 @@ -313,6 +312,16 @@ void neo1973_vibrator(int on) 274 415 gpio->GPBDAT &= ~(1 << 10); 275 416 } … … 316 457 + 317 458 #endif 459 Index: u-boot/common/console.c 460 =================================================================== 461 --- u-boot.orig/common/console.c 462 +++ u-boot/common/console.c 463 @@ -160,8 +160,12 @@ void fprintf (int file, const char *fmt, 464 465 /** U-Boot INITIAL CONSOLE-COMPATIBLE FUNCTION *****************************/ 466 467 +void (*console_poll_hook)(int activity); 468 + 469 int getc (void) 470 { 471 + while (console_poll_hook && !tstc()); 472 + 473 if (gd->flags & GD_FLG_DEVINIT) { 474 /* Get from the standard input */ 475 return fgetc (stdin); 476 @@ -171,7 +175,7 @@ int getc (void) 477 return serial_getc (); 478 } 479 480 -int tstc (void) 481 +static int do_tstc (void) 482 { 483 if (gd->flags & GD_FLG_DEVINIT) { 484 /* Test the standard input */ 485 @@ -182,6 +186,16 @@ int tstc (void) 486 return serial_tstc (); 487 } 488 489 +int tstc (void) 490 +{ 491 + int ret; 492 + 493 + ret = do_tstc(); 494 + if (console_poll_hook) 495 + console_poll_hook(ret); 496 + return ret; 497 +} 498 + 499 void putc (const char c) 500 { 501 #ifdef CONFIG_SILENT_CONSOLE 502 Index: u-boot/include/console.h 503 =================================================================== 504 --- u-boot.orig/include/console.h 505 +++ u-boot/include/console.h 506 @@ -33,6 +33,8 @@ 507 extern device_t *stdio_devices[] ; 508 extern char *stdio_names[MAX_FILES] ; 509 510 +extern void (*console_poll_hook)(int activity); 511 + 512 int console_realloc(int top); 513 514 #endif
Note: See TracChangeset
for help on using the changeset viewer.
