X-Git-Url: http://cloudbase.mooo.com/gitweb/z180-stamp.git/blobdiff_plain/a2907f2e2b2725679d6b3b8d3231f3d94c325014..9403f93922ea096bfdea4a81f1c34c5c044fcbbb:/avr/cmd_boot.c diff --git a/avr/cmd_boot.c b/avr/cmd_boot.c index b00d062..e26a8b1 100644 --- a/avr/cmd_boot.c +++ b/avr/cmd_boot.c @@ -10,15 +10,14 @@ /* * Misc boot support */ -#include "common.h" -#include +#include "cmd_boot.h" #include #include -#include "command.h" #include "cli_readline.h" /* console_buffer[] */ #include "cli.h" /* run_command() */ #include "env.h" +#include "eval_arg.h" #include "con-utils.h" #include "getopt-min.h" #include "z80-if.h" @@ -32,45 +31,11 @@ #undef const - -static void z80_load_mem(int_fast8_t verbosity, - const FLASH unsigned char data[], - const FLASH unsigned long *sections, - const FLASH unsigned long address[], - const FLASH unsigned long length_of_sections[]) +command_ret_t do_loadf(cmd_tbl_t *cmdtp UNUSED, uint_fast8_t flag UNUSED, int argc UNUSED, char * const argv[] UNUSED) { - uint32_t sec_base = 0; - - if (verbosity > 1) - printf_P(PSTR("Loading Z180 memory... \n")); - - for (unsigned sec = 0; sec < *sections; sec++) { - if (verbosity > 0) { - printf_P(PSTR(" From: 0x%.5lX to: 0x%.5lX (%5li bytes)\n"), - address[sec], - address[sec]+length_of_sections[sec] - 1, - length_of_sections[sec]); - } - - z80_write_block_P((const FLASH unsigned char *) &data[sec_base], /* src */ - address[sec], /* dest */ - length_of_sections[sec]); /* len */ - sec_base += length_of_sections[sec]; - } -} - -command_ret_t do_loadf(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) -{ - (void) cmdtp; (void) flag; (void) argc; (void) argv; - - if (z80_bus_state() & ZST_RUNNING) { - my_puts_P(PSTR("Can't load while CPU is running!\n")); - return CMD_RET_FAILURE; - } - if (!(z80_bus_cmd(Request) & ZST_ACQUIRED)) { - my_puts_P(PSTR("Bus timeout\n")); - return CMD_RET_FAILURE; - } + if (z80_bus_state() & ZST_RUNNING) + cmd_error(CMD_RET_FAILURE, ERUNNING, NULL); + z80_bus_request_or_exit(); z80_load_mem(2, hdrom, &hdrom_sections, hdrom_address, @@ -112,7 +77,7 @@ void print_vars(char *title) * -v verbose */ -command_ret_t do_bootcf(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) +command_ret_t do_bootcf(cmd_tbl_t *cmdtp UNUSED, uint_fast8_t flag UNUSED, int argc, char * const argv[]) { struct { uint8_t jr[2]; @@ -121,11 +86,11 @@ command_ret_t do_bootcf(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[ uint8_t sec_cnt; uint8_t part_id; uint16_t timeout; - uint8_t stop_stage; + uint8_t stages; } boot_param; struct { - uint8_t stop_stage; + uint8_t stages; uint8_t done; uint8_t result; uint8_t ide_stat; @@ -133,14 +98,13 @@ command_ret_t do_bootcf(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[ } boot_res; int_fast8_t verbosity = 0; - uint8_t stages; + uint8_t default_stages; uint32_t val; - - (void) cmdtp; (void) flag; + ERRNUM res = ESUCCESS; /* get default values */ memcpy_P(&boot_param, cfboot, sizeof boot_param); - stages = boot_param.stop_stage; + default_stages = boot_param.stages; /* reset getopt() */ optind = 0; @@ -152,11 +116,11 @@ command_ret_t do_bootcf(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[ verbosity++; break; case 'n': - if (boot_param.stop_stage > 0) - boot_param.stop_stage--; + if (boot_param.stages > 0) + boot_param.stages--; break; case 'a': - val = strtoul(optarg, NULL, 16); + val = eval_arg(optarg, NULL); if (val < 0x100 || val > 0xFE00) { printf_P(PSTR("Address out of range: 0x%.4lX\n"), val); return CMD_RET_FAILURE; @@ -164,7 +128,7 @@ command_ret_t do_bootcf(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[ boot_param.loadaddr = val; break; case 's': - val = strtoul(optarg, NULL, 16); + val = eval_arg(optarg, NULL); if (val > 255) { printf_P(PSTR("Start sector out of range: 0x%lX\n"), val); return CMD_RET_FAILURE; @@ -172,7 +136,7 @@ command_ret_t do_bootcf(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[ boot_param.sec_start = val; break; case 'c': - val = strtoul(optarg, NULL, 16); + val = eval_arg(optarg, NULL); if (val > 127) { printf_P(PSTR("Sector count out of range: 0x%lX\n"), val); return CMD_RET_FAILURE; @@ -180,15 +144,15 @@ command_ret_t do_bootcf(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[ boot_param.sec_cnt = val; break; case 't': - val = strtoul(optarg, NULL, 10); + val = eval_arg(optarg, NULL); if (val < 0x1 || val > 0xFFFF) { printf_P(PSTR("Timeout value out of range: 0x%lX\n"), val); return CMD_RET_FAILURE; } - boot_param.loadaddr = val; + boot_param.timeout = val; break; case 'i': - val = strtoul(optarg, NULL, 16); + val = eval_arg(optarg, NULL); if (val < 0x01 || val > 0xFF) { printf_P(PSTR("Partition id out of range: 0x%lX\n"), val); return CMD_RET_FAILURE; @@ -212,16 +176,9 @@ command_ret_t do_bootcf(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[ return CMD_RET_FAILURE; } - - - if (z80_bus_state() & ZST_RUNNING) { - my_puts_P(PSTR("CPU is allready running!\n")); - return CMD_RET_FAILURE; - } - if (!(z80_bus_cmd(Request) & ZST_ACQUIRED)) { - my_puts_P(PSTR("Bus timeout\n")); - return CMD_RET_FAILURE; - } + if (z80_bus_state() & ZST_RUNNING) + cmd_error(CMD_RET_FAILURE, ERUNNING, NULL); + z80_bus_request_or_exit(); z80_load_mem(verbosity, cfboot, &cfboot_sections, cfboot_address, @@ -231,11 +188,11 @@ command_ret_t do_bootcf(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[ cfboot_address[0], sizeof boot_param); z80_bus_cmd(Release); - if (boot_param.stop_stage == 0) { + if (boot_param.stages == 0) { printf_P(PSTR("Bootloader loaded at: 0x%.4X\n"), (uint16_t) cfboot_address[0]); } else { printf_P(PSTR("Executing %d of %d Bootloader stages...\n"), - boot_param.stop_stage, stages); + boot_param.stages, default_stages); z80_bus_cmd(Run); z80_bus_cmd(Release); @@ -257,12 +214,15 @@ command_ret_t do_bootcf(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[ z80_bus_cmd(Reset); my_puts_P(PSTR("Abort\n")); } else { - if (boot_param.stop_stage == stages) { + if (boot_param.stages == default_stages && + boot_res.stages == 0 && + boot_res.result == 0) { my_puts_P(PSTR("Booting...\n")); } else { z80_bus_cmd(Reset); + boot_res.stages++; printf_P(PSTR("Bootloader stopped at stage %d, result: %d, IDE stat/error: 0x%.02x/0x%.02x\n"), - boot_param.stop_stage - boot_res.stop_stage, + boot_param.stages - boot_res.stages, boot_res.result, boot_res.ide_stat, boot_res.ide_error); } } @@ -271,19 +231,17 @@ command_ret_t do_bootcf(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[ return CMD_RET_SUCCESS; } -command_ret_t do_busreq_pulse(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) +command_ret_t do_busreq_pulse(cmd_tbl_t *cmdtp UNUSED, uint_fast8_t flag UNUSED, int argc, char * const argv[]) { uint16_t count=1; - (void) cmdtp; (void) flag; - if (!(z80_bus_state() & ZST_RUNNING)) { printf_P(PSTR("## CPU is not running!\n")); return CMD_RET_FAILURE; } if (argc > 1) - count = (uint16_t) strtoul(argv[1], NULL, 16); + count = (uint16_t) eval_arg(argv[1], NULL); z80_bus_cmd(Request); while (count--) @@ -293,28 +251,42 @@ command_ret_t do_busreq_pulse(cmd_tbl_t *cmdtp, int flag, int argc, char * const } -command_ret_t do_go(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) +command_ret_t do_go(cmd_tbl_t *cmdtp UNUSED, uint_fast8_t flag UNUSED, int argc, char * const argv[]) { uint32_t addr; + bool hold = 0; - (void) cmdtp; (void) flag; + /* reset getopt() */ + optind = 0; - if (argc < 2) + int opt; + while ((opt = getopt(argc, argv, PSTR("h"))) != -1) { + switch (opt) { + case 'h': + hold = 1; + break; + default: /* '?' */ + return CMD_RET_USAGE; + } + } + argc -= optind; /* remaining arguments */ + + if (argc != 1) return CMD_RET_USAGE; - addr = strtoul(argv[1], NULL, 16); + addr = eval_arg(argv[optind], NULL); if (addr >= (1UL<<16)) { - printf_P(PSTR("## Startaddress 0x%05lx too high.\n" + printf_P(PSTR("Invalid startaddress: 0x%05lx\n" " (Out of logical address space (0x00000-0x0ffff))\n"), addr); return CMD_RET_FAILURE; } if (z80_bus_state() & ZST_RUNNING) { - printf_P(PSTR("## CPU allready running!\n")); + printf_P(PSTR("CPU already running!\n")); return CMD_RET_FAILURE; } - printf_P(PSTR("## Starting application at 0x%04lx ...\n"), addr); + printf_P(PSTR("Starting application at 0x%04lx ...\n"), addr); if (addr != 0) { uint8_t tmp[3]; @@ -326,13 +298,19 @@ command_ret_t do_go(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) z80_write(2, (addr >> 8)); z80_bus_cmd(Run); + _delay_us(10); z80_bus_cmd(M_Cycle); + _delay_us(10); z80_bus_cmd(M_Cycle); + _delay_us(10); z80_write_block(tmp, 0, 3); - } else + } else { + if (!hold) + z80_bus_cmd(Request); z80_bus_cmd(Run); - - z80_bus_cmd(Release); + } + if (!hold) + z80_bus_cmd(Release); return CMD_RET_SUCCESS; } @@ -345,20 +323,16 @@ void reset_cpu(bus_cmd_t mode) } -command_ret_t do_reset(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) +command_ret_t do_reset(cmd_tbl_t *cmdtp UNUSED, uint_fast8_t flag UNUSED, int argc UNUSED, char * const argv[] UNUSED) { - (void) cmdtp; (void) flag; (void) argc; (void) argv; - printf_P(PSTR("CPU now in reset state.\n")); reset_cpu(Reset); return CMD_RET_SUCCESS; } -command_ret_t do_restart(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) +command_ret_t do_restart(cmd_tbl_t *cmdtp UNUSED, uint_fast8_t flag UNUSED, int argc UNUSED, char * const argv[] UNUSED) { - (void) cmdtp; (void) flag; (void) argc; (void) argv; - reset_cpu(Restart); return CMD_RET_SUCCESS; @@ -380,17 +354,14 @@ void print_con_usage(char esc) ), esc + 0x40); } -command_ret_t do_console(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) +command_ret_t do_console(cmd_tbl_t *cmdtp UNUSED, uint_fast8_t flag UNUSED, int argc UNUSED, char * const argv[] UNUSED) { int ch; uint8_t pending; -// uint8_t help_prompt = 0; uint8_t code = 0; uint8_t state = 0; char esc_char = (char) getenv_ulong(PSTR(ENV_ESC_CHAR), 16, CONFIG_ESC_CHAR); - (void) cmdtp; (void) flag; (void) argc; (void) argv; - printf_P(PSTR("Connecting to CPU. Escape character is '^%c'.\n"), esc_char + 0x40); @@ -417,7 +388,7 @@ command_ret_t do_console(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv } break; case 2: - printf_P(PSTR("\n" + my_puts_P(PSTR("\n" "------------------------------------------------\n")); case 1: state = 0; @@ -435,7 +406,7 @@ command_ret_t do_console(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv case 'X': case 'Q': - printf_P(PSTR("\n")); + putchar('\n'); goto quit; break;