Felipe Neves
/
TEN_mbedos_simple_shell
TEN MBED OS Course shell utility
shell.cpp
- Committer:
- uLipe
- Date:
- 2017-01-29
- Revision:
- 0:1e8461adc480
File content as of revision 0:1e8461adc480:
/** * @brief our first hello world threaded program with MBED OS */ #include "mbed.h" #include "rtos.h" #include "shell.h" /* declare a thread reserved only for shell command handler */ const size_t shell_stk_size = 8192; uint8_t shell_stk[shell_stk_size]; Thread shell_thread(osPriorityNormal, shell_stk_size, &shell_stk[0]); /* reserve the debbuger uart to shell interface */ Serial pc_serial(SHELL_TXD,SHELL_RXD); static shell_callback_t shell_handler = NULL; static shell_usage_t shell_usage; static int argc = 0; static char *argv[16]; /** * @brief show help menu */ static void print_usage(void) { pc_serial.printf("## use with the syntax below: \n\r"); pc_serial.printf("## command <arg1> <arg2> ... <arg16> \n\r"); pc_serial.printf("## Available commands: \n\r"); if(shell_usage != NULL) { shell_usage((void *)&pc_serial); } } /** * @brief parse the command received via comport */ static void shell_parser (char *cmd, int size) { int cmd_ptr = 0; int arg_ptr = 0; int cmd_size = 0; char command_buffer[256]; /* copy to the root command */ memset(&command_buffer, 0, sizeof(command_buffer)); /* find the root command terminator (space) */ while(cmd_ptr < size) { if(cmd[cmd_ptr] == ' ') break; cmd_ptr++; } cmd_size = size - cmd_ptr; /* extract command arguments */ strncpy(&command_buffer[0], &cmd[cmd_ptr + 1], (size - cmd_ptr)); /* terminates the root command */ cmd[cmd_ptr] = 0; arg_ptr = 0; //pc_serial.printf("## command: %s \n\r", cmd); //pc_serial.printf("## arguments: %s \n\r", command_buffer); /* extract the further arguments */ while(arg_ptr < (cmd_size)) { argc++; *(argv + (argc- 1)) = &command_buffer[arg_ptr]; /* find terminator */ while(command_buffer[arg_ptr] != ' ') { arg_ptr++; } /* adds to argument list */ command_buffer[arg_ptr] = 0; arg_ptr++; // pc_serial.printf("## argument no: %d : %s \n\r", argc, argv[argc-1]); } /* finds and execute the command table */ if(shell_handler != NULL){ int ret = shell_handler(cmd, argc, argv, (void *)&pc_serial); if(ret < 0) { print_usage(); } }else { print_usage(); } } /** * @brief shell commands processing thread */ static void shell_task(void) { char serial_buffer[1024] = {0}; int read_ptr = 0; /* setup the serial as 115200 bps */ pc_serial.baud(115200); /* prints a welcome message */ pc_serial.printf("******************************************************************\n\r"); pc_serial.printf("*** Welcome to MbedOS Simple Shell application ****\n\r"); pc_serial.printf("*** Type some commands or just Enter key to see the available ****\n\r"); pc_serial.printf("******************************************************************\n\r"); pc_serial.printf(">>"); for(;;Thread::wait(50)) { /* check if we have character available */ if(pc_serial.readable()) { bool new_cmd = false; /* get the incoming character */ char c = pc_serial.getc(); if( (c == '\n') || (c == '\r')) { /* handle enter key */ new_cmd = true; pc_serial.printf("\n\r"); }else if( (c == 0x7F) || (c == 0x08)){ /* handle backspace and del keys */ pc_serial.printf("\033[1D"); pc_serial.putc(' '); pc_serial.printf("\033[1D"); read_ptr--; if(read_ptr < 0) read_ptr = 1023; serial_buffer[read_ptr] = ' '; } else { /* loopback the pressed key */ pc_serial.putc(c); /* store the incoming character on command circular buffer */ serial_buffer[read_ptr] = c; read_ptr = (read_ptr + 1) % 1024; } if(new_cmd != false) { /* command arrived, has other characters? */ if(read_ptr != 0) { shell_parser(&serial_buffer[0], read_ptr); } else { print_usage(); } /* reset the buffer command */ memset(&serial_buffer, 0, sizeof(serial_buffer)); read_ptr = 0; pc_serial.printf(">>"); } } } } void shell_set_command_handler(shell_callback_t sh) { shell_handler = sh; } void shell_set_cmd_list(shell_usage_t sh) { shell_usage = sh; } void shell_start(void) { shell_thread.start(shell_task); }