1 /*******************************************************************
2 Copyright (C) 2009 FreakLabs
5 Redistribution and use in source and binary forms, with or without
6 modification, are permitted provided that the following conditions
9 1. Redistributions of source code must retain the above copyright
10 notice, this list of conditions and the following disclaimer.
11 2. Redistributions in binary form must reproduce the above copyright
12 notice, this list of conditions and the following disclaimer in the
13 documentation and/or other materials provided with the distribution.
14 3. Neither the name of the the copyright holder nor the names of its contributors
15 may be used to endorse or promote products derived from this software
16 without specific prior written permission.
18 THIS SOFTWARE IS PROVIDED BY THE THE COPYRIGHT HOLDERS AND CONTRIBUTORS ``AS IS'' AND
19 ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
20 IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
21 ARE DISCLAIMED. IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE
22 FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
23 DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
24 OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
25 HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
26 LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
27 OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
30 Originally written by Christopher Wang aka Akiba.
31 Please post support questions to the FreakLabs forum.
32 *******************************************************************/
34 /**************************************************************************/
37 @author Christopher Wang (Freaklabs)
38 Modified by: K. Townsend (microBuilder.eu)
41 Original code taken from the FreakUSB Open Source USB Device Stack
42 http://freaklabs.org/index.php/FreakUSB-Open-Source-USB-Device-Stack.html
44 If it works well, you can thank Akiba at Freaklabs. If it fails
45 miserably, you can blame me (since parts of it it were rather
46 ungraciously modified). :-)
49 /**************************************************************************/
55 #include "project/cmd_tbl.h"
57 #ifdef CFG_PRINTF_UART
58 #include "core/uart/uart.h"
61 #ifdef CFG_PRINTF_USBCDC
62 #include "core/usbcdc/cdcuser.h"
63 static char usbcdcBuf
[32];
66 #if CFG_INTERFACE_ENABLEIRQ == 1
67 #include "core/gpio/gpio.h"
70 static uint8_t msg
[CFG_INTERFACE_MAXMSGSIZE
];
71 static uint8_t *msg_ptr
;
73 /**************************************************************************/
75 @brief Polls the relevant incoming message queue to see if anything
76 is waiting to be processed.
78 /**************************************************************************/
81 #if defined CFG_PRINTF_UART
82 while (uartRxBufferDataPending())
84 uint8_t c
= uartRxBufferRead();
89 #if defined CFG_PRINTF_USBCDC
90 int numBytesToRead
, numBytesRead
, numAvailByte
;
92 CDC_OutBufAvailChar (&numAvailByte
);
95 numBytesToRead
= numAvailByte
> 32 ? 32 : numAvailByte
;
96 numBytesRead
= CDC_RdOutBuf (&usbcdcBuf
[0], &numBytesToRead
);
98 for (i
= 0; i
< numBytesRead
; i
++)
106 /**************************************************************************/
108 @brief Handles a single incoming character. If a new line is
109 detected, the entire command will be passed to the command
110 parser. If a text character is detected, it will be added to
111 the message buffer until a new line is detected (up to the
112 maximum queue size, CFG_INTERFACE_MAXMSGSIZE).
115 The character to parse.
117 /**************************************************************************/
118 void cmdRx(uint8_t c
)
120 // read out the data in the buffer and echo it back to the host.
124 #if CFG_INTERFACE_DROPCR == 1
128 // terminate the msg and reset the msg ptr. then send
129 // it to the handler for processing.
131 #if CFG_INTERFACE_SILENTMODE == 0
132 printf("%s", CFG_PRINTF_NEWLINE
);
134 cmdParse((char *)msg
);
139 #if CFG_INTERFACE_SILENTMODE == 0
149 #if CFG_INTERFACE_SILENTMODE == 0
157 /**************************************************************************/
159 @brief Displays the command prompt. The text that appears is defined
162 /**************************************************************************/
163 static void cmdMenu()
165 #if CFG_INTERFACE_SILENTMODE == 0
166 printf(CFG_PRINTF_NEWLINE
);
167 printf(CFG_INTERFACE_PROMPT
);
169 #if CFG_INTERFACE_CONFIRMREADY == 1
170 printf("%s%s", CFG_INTERFACE_CONFIRMREADY_TEXT
, CFG_PRINTF_NEWLINE
);
174 /**************************************************************************/
176 @brief Parse the command line. This function tokenizes the command
177 input, then searches for the command table entry associated
178 with the commmand. Once found, it will jump to the
179 corresponding function.
182 The entire command string to be parsed
184 /**************************************************************************/
185 void cmdParse(char *cmd
)
190 argv
[i
] = strtok(cmd
, " ");
193 argv
[++i
] = strtok(NULL
, " ");
194 } while ((i
< 30) && (argv
[i
] != NULL
));
197 for (i
=0; i
< CMD_COUNT
; i
++)
199 if (!strcmp(argv
[0], cmd_tbl
[i
].command
))
201 if ((argc
== 2) && !strcmp (argv
[1], "?"))
203 // Display parameter help menu on 'command ?'
204 printf ("%s%s%s", cmd_tbl
[i
].description
, CFG_PRINTF_NEWLINE
, CFG_PRINTF_NEWLINE
);
205 printf ("%s%s", cmd_tbl
[i
].parameters
, CFG_PRINTF_NEWLINE
);
207 else if ((argc
- 1) < cmd_tbl
[i
].minArgs
)
209 // Too few arguments supplied
210 #if CFG_INTERFACE_SHORTERRORS == 1
211 printf ("%s%s", CFG_INTERFACE_SHORTERRORS_TOOFEWARGS
, CFG_PRINTF_NEWLINE
);
213 printf ("Too few arguments (%d expected)%s", cmd_tbl
[i
].minArgs
, CFG_PRINTF_NEWLINE
);
214 printf ("%sType '%s ?' for more information%s%s", CFG_PRINTF_NEWLINE
, cmd_tbl
[i
].command
, CFG_PRINTF_NEWLINE
, CFG_PRINTF_NEWLINE
);
217 else if ((argc
- 1) > cmd_tbl
[i
].maxArgs
)
219 // Too many arguments supplied
220 #if CFG_INTERFACE_SHORTERRORS == 1
221 printf ("%s%s", CFG_INTERFACE_SHORTERRORS_TOOMANYARGS
, CFG_PRINTF_NEWLINE
);
223 printf ("Too many arguments (%d maximum)%s", cmd_tbl
[i
].maxArgs
, CFG_PRINTF_NEWLINE
);
224 printf ("%sType '%s ?' for more information%s%s", CFG_PRINTF_NEWLINE
, cmd_tbl
[i
].command
, CFG_PRINTF_NEWLINE
, CFG_PRINTF_NEWLINE
);
229 #if CFG_INTERFACE_ENABLEIRQ != 0
230 // Set the IRQ pin high at start of a command
231 gpioSetValue(CFG_INTERFACE_IRQPORT
, CFG_INTERFACE_IRQPIN
, 1);
233 // Dispatch command to the appropriate function
234 cmd_tbl
[i
].func(argc
- 1, &argv
[1]);
235 #if CFG_INTERFACE_ENABLEIRQ != 0
236 // Set the IRQ pin low to signal the end of a command
237 gpioSetValue(CFG_INTERFACE_IRQPORT
, CFG_INTERFACE_IRQPIN
, 0);
241 // Refresh the command prompt
246 // Command not recognized
247 #if CFG_INTERFACE_SHORTERRORS == 1
248 printf ("%s%s", CFG_INTERFACE_SHORTERRORS_UNKNOWNCOMMAND
, CFG_PRINTF_NEWLINE
);
250 printf("Command not recognized: '%s'%s%s", cmd
, CFG_PRINTF_NEWLINE
, CFG_PRINTF_NEWLINE
);
251 #if CFG_INTERFACE_SILENTMODE == 0
252 printf("Type '?' for a list of all available commands%s", CFG_PRINTF_NEWLINE
);
259 /**************************************************************************/
261 @brief Initialises the command line using the appropriate interface
263 /**************************************************************************/
266 #if defined CFG_INTERFACE && defined CFG_INTERFACE_UART
267 // Check if UART is already initialised
268 uart_pcb_t
*pcb
= uartGetPCB();
269 if (!pcb
->initialised
)
271 uartInit(CFG_UART_BAUDRATE
);
275 #if CFG_INTERFACE_ENABLEIRQ != 0
276 // Set IRQ pin as output
277 gpioSetDir(CFG_INTERFACE_IRQPORT
, CFG_INTERFACE_IRQPIN
, gpioDirection_Output
);
278 gpioSetValue(CFG_INTERFACE_IRQPORT
, CFG_INTERFACE_IRQPIN
, 1);
287 // Set the IRQ pin low by default
288 #if CFG_INTERFACE_ENABLEIRQ != 0
289 gpioSetValue(CFG_INTERFACE_IRQPORT
, CFG_INTERFACE_IRQPIN
, 0);
293 /**************************************************************************/
295 'help' command handler
297 /**************************************************************************/
298 void cmd_help(uint8_t argc
, char **argv
)
302 printf("Command Description%s", CFG_PRINTF_NEWLINE
);
303 printf("------- -----------%s", CFG_PRINTF_NEWLINE
);
305 // Display full command list
306 for (i
=0; i
< CMD_COUNT
; i
++)
308 if (!cmd_tbl
[i
].hidden
)
310 printf ("%-10s %s%s", cmd_tbl
[i
].command
, cmd_tbl
[i
].description
, CFG_PRINTF_NEWLINE
);
314 printf("%sCommand parameters can be seen by entering: <command-name> ?%s", CFG_PRINTF_NEWLINE
, CFG_PRINTF_NEWLINE
);