]> cloudbase.mooo.com Git - z180-stamp.git/blame - avr/cmd_boot.c
esc_char environment variable
[z180-stamp.git] / avr / cmd_boot.c
CommitLineData
35edb766
L
1/*
2 * (C) Copyright 2014 Leo C. <erbl259-lmu@yahoo.de>
3 *
4 * (C) Copyright 2000-2003
5 * Wolfgang Denk, DENX Software Engineering, wd@denx.de.
6 *
7 * SPDX-License-Identifier: GPL-2.0+
8 */
534e1dfc
L
9
10/*
11 * Misc boot support
12 */
13#include "common.h"
14#include <stdlib.h>
8a7decea 15#include <ctype.h>
89adce76 16#include <util/atomic.h>
534e1dfc
L
17
18#include "command.h"
612a6965 19#include "env.h"
89adce76 20#include "con-utils.h"
534e1dfc 21#include "z80-if.h"
89adce76 22#include "z180-serv.h"
8a7decea 23#include "debug.h"
534e1dfc
L
24
25/* ugly hack to get Z180 loadfile into flash memory */
26#define const const FLASH
27#include "../z180/hdrom.h"
28#undef const
29
30
31
32static void z80_load_mem(void)
33{
34 unsigned sec = 0;
35 uint32_t sec_base = hdrom_start;
36
37 printf_P(PSTR("Loading Z180 memory... \n"));
38
39 while (sec < hdrom_sections) {
40 printf_P(PSTR(" From: 0x%.5lX to: 0x%.5lX (%5li bytes)\n"),
41 hdrom_address[sec],
42 hdrom_address[sec]+hdrom_length_of_sections[sec] - 1,
43 hdrom_length_of_sections[sec]);
44
ea6971b8 45 z80_write_block_P((const FLASH unsigned char *) &hdrom[sec_base], /* src */
41d36f28 46 hdrom_address[sec], /* dest */
534e1dfc 47 hdrom_length_of_sections[sec]); /* len */
534e1dfc
L
48 sec_base+=hdrom_length_of_sections[sec];
49 sec++;
50 }
51}
52
d0581f88 53command_ret_t do_loadf(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
534e1dfc
L
54{
55 (void) cmdtp; (void) flag; (void) argc; (void) argv;
56
6035a17b 57 if (z80_bus_state() & ZST_RUNNING) {
612a6965 58 my_puts_P(PSTR("Can't load while CPU is running!\n"));
6035a17b 59 return CMD_RET_FAILURE;
534e1dfc 60 }
612a6965
L
61 if (!(z80_bus_cmd(Request) & ZST_ACQUIRED)) {
62 my_puts_P(PSTR("Bus timeout\n"));
63 return CMD_RET_FAILURE;
64 }
534e1dfc 65 z80_load_mem();
612a6965 66 z80_bus_cmd(Release);
6035a17b 67
d0581f88 68 return CMD_RET_SUCCESS;
534e1dfc
L
69}
70
71
d0581f88 72command_ret_t do_busreq_pulse(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
534e1dfc 73{
f338df2a 74 uint16_t count=1;
534e1dfc 75
f338df2a 76 (void) cmdtp; (void) flag;
534e1dfc 77
6035a17b 78 if (!(z80_bus_state() & ZST_RUNNING)) {
f338df2a 79 printf_P(PSTR("## CPU is not running!\n"));
d0581f88 80 return CMD_RET_FAILURE;
534e1dfc
L
81 }
82
f338df2a
L
83 if (argc > 1)
84 count = (uint16_t) strtoul(argv[2], NULL, 16);
85
62f624d3 86 z80_bus_cmd(Request);
f338df2a 87 while (count--)
62f624d3 88 z80_bus_cmd(M_Cycle);
534e1dfc 89
d0581f88 90 return CMD_RET_SUCCESS;
f338df2a
L
91}
92
93
d0581f88 94command_ret_t do_go(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
f338df2a
L
95{
96 uint32_t addr;
97
98 (void) cmdtp; (void) flag;
6035a17b 99
f338df2a
L
100 if (argc < 2)
101 return CMD_RET_USAGE;
102 addr = strtoul(argv[1], NULL, 16);
103 if (addr >= (1UL<<16)) {
534e1dfc
L
104 printf_P(PSTR("## Startaddress 0x%05lx too high.\n"
105 " (Out of logical address space (0x00000-0x0ffff))\n"),
106 addr);
d0581f88 107 return CMD_RET_FAILURE;
6035a17b 108 }
f338df2a 109
6035a17b 110 if (z80_bus_state() & ZST_RUNNING) {
f338df2a 111 printf_P(PSTR("## CPU allready running!\n"));
d0581f88 112 return CMD_RET_FAILURE;
534e1dfc
L
113 }
114
f338df2a
L
115 printf_P(PSTR("## Starting application at 0x%04lx ...\n"), addr);
116
117 if (addr != 0) {
118 uint8_t tmp[3];
119 uint_fast8_t i;
6035a17b 120
62f624d3 121 z80_bus_cmd(Request);
f338df2a
L
122 for (i = 0; i < 3; i++)
123 tmp[i] = z80_read(i);
124 z80_write(0, 0xc3);
125 z80_write(1, addr);
126 z80_write(2, (addr >> 8));
127
62f624d3
L
128 z80_bus_cmd(Run);
129 z80_bus_cmd(M_Cycle);
130 z80_bus_cmd(M_Cycle);
f338df2a
L
131 for (i = 0; i < 3; i++)
132 z80_write(i, tmp[i]);
133 } else
62f624d3 134 z80_bus_cmd(Run);
6035a17b 135
62f624d3 136 z80_bus_cmd(Release);
f338df2a 137
d0581f88 138 return CMD_RET_SUCCESS;
534e1dfc
L
139}
140
8a7decea
L
141static
142void reset_cpu(bus_cmd_t mode)
143{
144 restart_z180_serv();
145 z80_bus_cmd(mode);
146}
147
148
d0581f88 149command_ret_t do_reset(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
534e1dfc
L
150{
151 (void) cmdtp; (void) flag; (void) argc; (void) argv;
152
612a6965 153 printf_P(PSTR("CPU now in reset state.\n"));
534e1dfc 154
8a7decea 155 reset_cpu(Reset);
d0581f88 156 return CMD_RET_SUCCESS;
534e1dfc
L
157}
158
d0581f88 159command_ret_t do_restart(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
534e1dfc
L
160{
161 (void) cmdtp; (void) flag; (void) argc; (void) argv;
162
8a7decea 163 reset_cpu(Restart);
534e1dfc 164
d0581f88 165 return CMD_RET_SUCCESS;
534e1dfc
L
166}
167
8a7decea
L
168static
169void print_con_usage(char esc)
170{ printf_P(PSTR("\n"
171 "------------------------------------------------\n"
172 " ?,H - This Help\n"
173 " R - Reset (Restart) CPU\n"
174 " Q,X - Return to command line\n"
612a6965
L
175 " \\ - code input:\n"
176 " \\nnn 3 decimal digits character code\n"
177 " \\Xhh 2 hexadecimal digits character code\n"
178 " ^%c - (Escape char) Type again to send itself\n"
8a7decea
L
179 "key>"
180 ), esc + 0x40);
181}
89adce76
L
182
183command_ret_t do_console(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
184{
185 int ch;
8a7decea
L
186 uint8_t pending;
187// uint8_t help_prompt = 0;
188 uint8_t code = 0;
189 uint8_t state = 0;
612a6965 190 char esc_char = (char) getenv_ulong(PSTR(ENV_ESC_CHAR), 16, CONFIG_ESC_CHAR);
ea6971b8 191
89adce76
L
192 (void) cmdtp; (void) flag; (void) argc; (void) argv;
193
194
195 while (1) {
196
8a7decea 197 ATOMIC_BLOCK(ATOMIC_FORCEON) {
89adce76
L
198 pending = (Stat & S_CON_PENDING) != 0;
199 Stat &= ~S_CON_PENDING;
200 }
3ad4143b
L
201 if (pending) {
202 uint8_t count = 100;
203 while ((ch = z80_memfifo_getc(fifo_conout)) >= 0 && --count)
89adce76 204 putchar(ch);
3ad4143b 205 }
89adce76
L
206
207 if ((ch = my_getchar(0)) >= 0) {
208 switch (state) {
209 case 0:
612a6965 210 if (ch == esc_char) {
89adce76
L
211 state = 1;
212 /* TODO: Timer starten */
213 } else {
214 z80_memfifo_putc(fifo_conin, ch);
ea6971b8 215 }
89adce76 216 break;
8a7decea
L
217 case 2:
218 printf_P(PSTR("\n"
219 "------------------------------------------------\n"));
89adce76 220 case 1:
8a7decea
L
221 state = 0;
222 switch (toupper(ch)) {
89adce76 223
8a7decea
L
224 case '?':
225 case 'H':
612a6965 226 print_con_usage(esc_char);
8a7decea 227 state = 2;
89adce76
L
228 break;
229
8a7decea
L
230 case 'R':
231 reset_cpu(Restart);
89adce76
L
232 break;
233
8a7decea 234 case 'X':
89adce76 235 case 'Q':
889202c4 236 printf_P(PSTR("\n"));
89adce76
L
237 goto quit;
238 break;
239
8a7decea
L
240 case '\\':
241 code = 0;
242 state = 3;
243 break;
244
8a7decea 245 default:
612a6965
L
246 if (ch == esc_char)
247 z80_memfifo_putc(fifo_conin, ch);
8a7decea
L
248 break;
249 }
250 break;
251 case 3:
252 if (toupper(ch) == 'X') {
253 state = 6;
254 break;
255 }
256 /* fall thru */
257 case 4:
258 case 5:
259 if (isdigit(ch)) {
260 code = code * 10 + ch - '0';
261 state++;
262 }
263 if (state > 5) {
264 z80_memfifo_putc(fifo_conin, code);
265 state = 0;
266 }
267 break;
268 case 6:
269 case 7:
270 if (isxdigit(ch)) {
271 ch = toupper(ch);
272 if (ch >= 'A')
273 ch -= 'A' - 10;
274 code = code * 16 + ch - '0';
275 state++;
276 }
277 if (state > 7) {
278 z80_memfifo_putc(fifo_conin, code);
279 state = 0;
89adce76 280 }
89adce76
L
281 break;
282 }
283 }
89adce76
L
284 }
285quit:
89adce76
L
286 return CMD_RET_SUCCESS;
287}