2 * Copyright © 2009 Keith Packard <keithp@keithp.com>
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; version 2 of the License.
8 * This program is distributed in the hope that it will be useful, but
9 * WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11 * General Public License for more details.
13 * You should have received a copy of the GNU General Public License along
14 * with this program; if not, write to the Free Software Foundation, Inc.,
15 * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
21 #define SYNTAX_ERROR 2
24 static __xdata uint16_t lex_i;
25 static __xdata uint8_t lex_c;
26 static __xdata uint8_t lex_status;
27 static __xdata uint8_t lex_echo;
31 static __xdata uint8_t cmd_line[CMD_LEN];
32 static __xdata uint8_t cmd_len;
33 static __xdata uint8_t cmd_i;
40 ao_usb_putchar((uint8_t) c);
52 return (char) ao_usb_getchar();
73 /* backspace/delete */
74 if (c == '\010' || c == '\177') {
77 put_string("\010 \010");
85 while (cmd_len != 0) {
87 put_string("\010 \010");
103 if (cmd_len >= CMD_LEN - 2) {
108 cmd_line[cmd_len++] = c;
112 cmd_line[cmd_len++] = '\n';
113 cmd_line[cmd_len++] = '\0';
122 lex_c = cmd_line[cmd_i++];
131 putchar(v + ('a' - 10));
138 for (i = 3; i >= 0; i--)
139 putnibble((v >> (i << 2)) & 0xf);
145 putnibble((v >> 4) & 0xf);
154 static uint8_t __xdata num_buffer[NUM_LEN];
155 uint8_t __xdata * __xdata num_ptr = num_buffer + NUM_LEN;
156 uint8_t __xdata neg = 0;
164 *--num_ptr = '0' + i % 10;
169 while (num_ptr != num_buffer)
171 put_string(num_buffer);
178 while (lex_c == ' ' || lex_c == '\t')
185 __xdata uint8_t r = LEX_ERROR;
190 if ('0' <= lex_c && lex_c <= '9')
191 lex_i = (lex_i << 4) | (lex_c - '0');
192 else if ('a' <= lex_c && lex_c <= 'f')
193 lex_i = (lex_i << 4) | (lex_c - 'a' + 10);
194 else if ('A' <= lex_c && lex_c <= 'F')
195 lex_i = (lex_i << 4) | (lex_c - 'A' + 10);
209 __xdata uint8_t r = LEX_ERROR;
214 if ('0' <= lex_c && lex_c <= '9')
215 lex_i = (lex_i * 10 ) | (lex_c - '0');
229 while (lex_c != '\n')
236 __xdata struct ao_adc packet;
238 put_string("tick: ");
240 put_string(" accel: ");
241 puti(packet.accel >> 4);
242 put_string(" pres: ");
243 puti(packet.pres >> 4);
244 put_string(" temp: ");
245 puti(packet.temp >> 4);
246 put_string(" batt: ");
247 puti(packet.v_batt >> 4);
248 put_string(" drogue: ");
249 puti(packet.sense_d >> 4);
250 put_string(" main: ");
251 puti(packet.sense_m >> 4);
256 gps_dump(void) __reentrant
258 ao_mutex_get(&ao_gps_mutex);
259 if (ao_gps_data.flags & AO_GPS_VALID) {
260 printf("GPS %2d:%02d:%02d %2d°%2d.%04d'%c %2d°%2d.%04d'%c %5dm %2d sat\n",
264 ao_gps_data.latitude.degrees,
265 ao_gps_data.latitude.minutes,
266 ao_gps_data.latitude.minutes_fraction,
267 (ao_gps_data.flags & AO_GPS_LATITUDE_MASK) == AO_GPS_LATITUDE_NORTH ?
269 ao_gps_data.longitude.degrees,
270 ao_gps_data.longitude.minutes,
271 ao_gps_data.longitude.minutes_fraction,
272 (ao_gps_data.flags & AO_GPS_LONGITUDE_MASK) == AO_GPS_LONGITUDE_WEST ?
274 ao_gps_data.altitude,
275 (ao_gps_data.flags & AO_GPS_NUM_SAT_MASK) >> AO_GPS_NUM_SAT_SHIFT);
277 printf("GPS %2d sat\n",
278 (ao_gps_data.flags & AO_GPS_NUM_SAT_MASK) >> AO_GPS_NUM_SAT_SHIFT);;
280 ao_mutex_put(&ao_gps_mutex);
287 __xdata uint8_t * __xdata start, * __xdata end;
290 start = (uint8_t __xdata *) lex_i;
292 end = (uint8_t __xdata *) lex_i;
293 if (lex_status != SUCCESS)
296 while (start <= end) {
300 put16((uint16_t) start);
314 __xdata uint16_t block;
319 if (lex_status != SUCCESS)
329 ao_ee_read(((uint32_t) block << 8) | i, &b, 1);
339 __xdata uint16_t block;
341 __xdata uint16_t len;
343 __xdata uint32_t addr;
349 addr = ((uint32_t) block << 8) | i;
352 if (lex_status != SUCCESS)
356 if (lex_status != SUCCESS)
359 ao_ee_write(addr, &b, 1);
369 lex_echo = lex_i != 0;
392 if (lex_status != SUCCESS)
394 ao_dbg_send_byte(lex_i);
401 __xdata uint16_t count;
403 __xdata uint8_t byte;
405 if (lex_status != SUCCESS)
409 lex_status = SYNTAX_ERROR;
412 for (i = 0; i < count; i++) {
413 if (i && (i & 7) == 0)
415 byte = ao_dbg_recv_byte();
428 if ('0' <= c && c <= '9')
430 if ('a' <= c && c <= 'f')
431 return c - ('a' - 10);
432 if ('A' <= c && c <= 'F')
433 return c - ('A' - 10);
434 lex_status = LEX_ERROR;
441 __xdata uint16_t count;
442 __xdata uint16_t addr;
450 if (lex_status != SUCCESS)
452 ao_dbg_start_transfer(addr);
457 b = ao_dbg_read_byte();
460 ao_dbg_end_transfer();
467 __xdata uint16_t count;
468 __xdata uint16_t addr;
475 if (lex_status != SUCCESS)
477 ao_dbg_start_transfer(addr);
479 b = getnibble() << 4;
481 if (lex_status != SUCCESS)
483 ao_dbg_write_byte(b);
485 ao_dbg_end_transfer();
491 __xdata uint8_t more;
493 for (more = ao_log_dump_first(); more; more = ao_log_dump_next()) {
494 putchar(ao_log_dump.type);
496 put16(ao_log_dump.tick);
498 put16(ao_log_dump.u.anon.d0);
500 put16(ao_log_dump.u.anon.d1);
509 while (lex_c != '\n') {
510 ao_serial_putchar(lex_c);
515 static const uint8_t help_txt[] =
516 "All numbers are in hex\n"
517 "? Print this message\n"
518 "a Display current ADC values\n"
519 "g Display current GPS values\n"
520 "d <start> <end> Dump memory\n"
521 "e <block> Dump a block of EEPROM data\n"
522 "w <block> <start> <len> <data> ... Write data to EEPROM\n"
523 "l Dump last flight log\n"
524 "E <0 off, 1 on> Set command echo mode\n"
525 "S<data> Send data to serial line\n"
526 "T Show task states\n"
528 "Target debug commands:\n"
529 "D Enable debug mode\n"
531 "P <byte> ... Put data to debug port\n"
532 "G <count> Get data from debug port\n"
533 "O <count> <addr> Output <count> bytes to target at <addr>\n"
534 "I <count> <addr> Input <count> bytes to target at <addr>\n"
540 put_string(help_txt);
549 put_string("Syntax error\n");
556 ao_cmd(void *parameters)
621 lex_status = SYNTAX_ERROR;
629 __xdata struct ao_task ao_cmd_task;
634 ao_add_task(&ao_cmd_task, ao_cmd, "cmd");