fsl_shell.h 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337
  1. /*
  2. * Copyright (c) 2015, Freescale Semiconductor, Inc.
  3. * Copyright 2016-2020 NXP
  4. * All rights reserved.
  5. *
  6. * SPDX-License-Identifier: BSD-3-Clause
  7. */
  8. #ifndef __FSL_SHELL_H__
  9. #define __FSL_SHELL_H__
  10. /*!
  11. * @addtogroup SHELL
  12. * @{
  13. */
  14. #include "fsl_common.h"
  15. #include "fsl_component_serial_manager.h"
  16. #include "fsl_component_generic_list.h"
  17. /*******************************************************************************
  18. * Definitions
  19. ******************************************************************************/
  20. /*! @brief Whether use non-blocking mode. */
  21. #ifndef SHELL_NON_BLOCKING_MODE
  22. #define SHELL_NON_BLOCKING_MODE SERIAL_MANAGER_NON_BLOCKING_MODE
  23. #endif
  24. /*! @brief Macro to set on/off auto-complete feature. */
  25. #define SHELL_AUTO_COMPLETE (1U)
  26. /*! @brief Macro to set console buffer size. */
  27. #ifndef SHELL_BUFFER_SIZE
  28. #define SHELL_BUFFER_SIZE (64U)
  29. #endif
  30. /*! @brief Macro to set maximum arguments in command. */
  31. #define SHELL_MAX_ARGS (8U)
  32. /*! @brief Macro to set maximum count of history commands. */
  33. #ifndef SHELL_HISTORY_COUNT
  34. #define SHELL_HISTORY_COUNT (3U)
  35. #endif
  36. /*! @brief Macro to bypass arguments check */
  37. #define SHELL_IGNORE_PARAMETER_COUNT (0xFF)
  38. /*! @brief The handle size of the shell module. It is the sum of the SHELL_HISTORY_COUNT * SHELL_BUFFER_SIZE +
  39. * SHELL_BUFFER_SIZE + SERIAL_MANAGER_READ_HANDLE_SIZE + SERIAL_MANAGER_WRITE_HANDLE_SIZE*/
  40. #define SHELL_HANDLE_SIZE \
  41. (160U + SHELL_HISTORY_COUNT * SHELL_BUFFER_SIZE + SHELL_BUFFER_SIZE + SERIAL_MANAGER_READ_HANDLE_SIZE + \
  42. SERIAL_MANAGER_WRITE_HANDLE_SIZE)
  43. /*! @brief Macro to determine whether use common task. */
  44. #ifndef SHELL_USE_COMMON_TASK
  45. #define SHELL_USE_COMMON_TASK (0U)
  46. #endif
  47. /*! @brief Macro to set shell task priority. */
  48. #ifndef SHELL_TASK_PRIORITY
  49. #define SHELL_TASK_PRIORITY (2U)
  50. #endif
  51. /*! @brief Macro to set shell task stack size. */
  52. #ifndef SHELL_TASK_STACK_SIZE
  53. #define SHELL_TASK_STACK_SIZE (1000U)
  54. #endif
  55. /*! @brief Shell status */
  56. typedef enum _shell_status
  57. {
  58. kStatus_SHELL_Success = kStatus_Success, /*!< Success */
  59. kStatus_SHELL_Error = MAKE_STATUS(kStatusGroup_SHELL, 1), /*!< Failed */
  60. kStatus_SHELL_OpenWriteHandleFailed = MAKE_STATUS(kStatusGroup_SHELL, 2), /*!< Open write handle failed */
  61. kStatus_SHELL_OpenReadHandleFailed = MAKE_STATUS(kStatusGroup_SHELL, 3), /*!< Open read handle failed */
  62. } shell_status_t;
  63. /*! @brief The handle of the shell module */
  64. typedef void *shell_handle_t;
  65. /*! @brief User command function prototype. */
  66. typedef shell_status_t (*cmd_function_t)(shell_handle_t shellHandle, int32_t argc, char **argv);
  67. /*! @brief User command data configuration structure. */
  68. typedef struct _shell_command
  69. {
  70. const char *pcCommand; /*!< The command that is executed. For example "help". It must be all lower case. */
  71. char *pcHelpString; /*!< String that describes how to use the command. It should start with the command itself,
  72. and end with "\r\n". For example "help: Returns a list of all the commands\r\n". */
  73. const cmd_function_t
  74. pFuncCallBack; /*!< A pointer to the callback function that returns the output generated by the command. */
  75. uint8_t cExpectedNumberOfParameters; /*!< Commands expect a fixed number of parameters, which may be zero. */
  76. list_element_t link; /*!< link of the element */
  77. } shell_command_t;
  78. /*!
  79. * @brief Defines the shell handle
  80. *
  81. * This macro is used to define a 4 byte aligned shell handle.
  82. * Then use "(shell_handle_t)name" to get the shell handle.
  83. *
  84. * The macro should be global and could be optional. You could also define shell handle by yourself.
  85. *
  86. * This is an example,
  87. * @code
  88. * SHELL_HANDLE_DEFINE(shellHandle);
  89. * @endcode
  90. *
  91. * @param name The name string of the shell handle.
  92. */
  93. #define SHELL_HANDLE_DEFINE(name) uint32_t name[((SHELL_HANDLE_SIZE + sizeof(uint32_t) - 1U) / sizeof(uint32_t))]
  94. #if defined(__ICCARM__)
  95. /* disable misra 19.13 */
  96. _Pragma("diag_suppress=Pm120")
  97. #endif
  98. /*!
  99. * @brief Defines the shell command structure
  100. *
  101. * This macro is used to define the shell command structure #shell_command_t.
  102. * And then uses the macro SHELL_COMMAND to get the command structure pointer.
  103. * The macro should not be used in any function.
  104. *
  105. * This is a example,
  106. * @code
  107. * SHELL_COMMAND_DEFINE(exit, "\r\n\"exit\": Exit program\r\n", SHELL_ExitCommand, 0);
  108. * SHELL_RegisterCommand(s_shellHandle, SHELL_COMMAND(exit));
  109. * @endcode
  110. *
  111. * @param command The command string of the command. The double quotes do not need. Such as exit for "exit",
  112. * help for "Help", read for "read".
  113. * @param descriptor The description of the command is used for showing the command usage when "help" is typing.
  114. * @param callback The callback of the command is used to handle the command line when the input command is matched.
  115. * @param paramCount The max parameter count of the current command.
  116. */
  117. #define SHELL_COMMAND_DEFINE(command, descriptor, callback, paramCount) \
  118. \
  119. shell_command_t g_shellCommand##command = { \
  120. (#command), (descriptor), (callback), (paramCount), {0}, \
  121. }
  122. /*!
  123. * @brief Gets the shell command pointer
  124. *
  125. * This macro is used to get the shell command pointer. The macro should not be used before the macro
  126. * SHELL_COMMAND_DEFINE is used.
  127. *
  128. * @param command The command string of the command. The double quotes do not need. Such as exit for "exit",
  129. * help for "Help", read for "read".
  130. */
  131. #define SHELL_COMMAND(command) &g_shellCommand##command
  132. #if defined(__ICCARM__)
  133. _Pragma("diag_default=Pm120")
  134. #endif
  135. /*******************************************************************************
  136. * API
  137. ******************************************************************************/
  138. #if defined(__cplusplus)
  139. extern "C"
  140. {
  141. #endif /* _cplusplus */
  142. /*!
  143. * @name Shell functional operation
  144. * @{
  145. */
  146. /*!
  147. * @brief Initializes the shell module
  148. *
  149. * This function must be called before calling all other Shell functions.
  150. * Call operation the Shell commands with user-defined settings.
  151. * The example below shows how to set up the Shell and
  152. * how to call the SHELL_Init function by passing in these parameters.
  153. * This is an example.
  154. * @code
  155. * static SHELL_HANDLE_DEFINE(s_shellHandle);
  156. * SHELL_Init((shell_handle_t)s_shellHandle, (serial_handle_t)s_serialHandle, "Test@SHELL>");
  157. * @endcode
  158. * @param shellHandle Pointer to point to a memory space of size #SHELL_HANDLE_SIZE allocated by the caller.
  159. * The handle should be 4 byte aligned, because unaligned access doesn't be supported on some devices.
  160. * You can define the handle in the following two ways:
  161. * #SHELL_HANDLE_DEFINE(shellHandle);
  162. * or
  163. * uint32_t shellHandle[((SHELL_HANDLE_SIZE + sizeof(uint32_t) - 1U) / sizeof(uint32_t))];
  164. * @param serialHandle The serial manager module handle pointer.
  165. * @param prompt The string prompt pointer of Shell. Only the global variable can be passed.
  166. * @retval kStatus_SHELL_Success The shell initialization succeed.
  167. * @retval kStatus_SHELL_Error An error occurred when the shell is initialized.
  168. * @retval kStatus_SHELL_OpenWriteHandleFailed Open the write handle failed.
  169. * @retval kStatus_SHELL_OpenReadHandleFailed Open the read handle failed.
  170. */
  171. shell_status_t SHELL_Init(shell_handle_t shellHandle, serial_handle_t serialHandle, char *prompt);
  172. /*!
  173. * @brief Registers the shell command
  174. *
  175. * This function is used to register the shell command by using the command configuration shell_command_config_t.
  176. * This is a example,
  177. * @code
  178. * SHELL_COMMAND_DEFINE(exit, "\r\n\"exit\": Exit program\r\n", SHELL_ExitCommand, 0);
  179. * SHELL_RegisterCommand(s_shellHandle, SHELL_COMMAND(exit));
  180. * @endcode
  181. * @param shellHandle The shell module handle pointer.
  182. * @param shellCommand The command element.
  183. * @retval kStatus_SHELL_Success Successfully register the command.
  184. * @retval kStatus_SHELL_Error An error occurred.
  185. */
  186. shell_status_t SHELL_RegisterCommand(shell_handle_t shellHandle, shell_command_t * shellCommand);
  187. /*!
  188. * @brief Unregisters the shell command
  189. *
  190. * This function is used to unregister the shell command.
  191. *
  192. * @param shellCommand The command element.
  193. * @retval kStatus_SHELL_Success Successfully unregister the command.
  194. */
  195. shell_status_t SHELL_UnregisterCommand(shell_command_t * shellCommand);
  196. /*!
  197. * @brief Sends data to the shell output stream.
  198. *
  199. * This function is used to send data to the shell output stream.
  200. *
  201. * @param shellHandle The shell module handle pointer.
  202. * @param buffer Start address of the data to write.
  203. * @param length Length of the data to write.
  204. * @retval kStatus_SHELL_Success Successfully send data.
  205. * @retval kStatus_SHELL_Error An error occurred.
  206. */
  207. shell_status_t SHELL_Write(shell_handle_t shellHandle, const char *buffer, uint32_t length);
  208. /*!
  209. * @brief Writes formatted output to the shell output stream.
  210. *
  211. * Call this function to write a formatted output to the shell output stream.
  212. *
  213. * @param shellHandle The shell module handle pointer.
  214. *
  215. * @param formatString Format string.
  216. * @return Returns the number of characters printed or a negative value if an error occurs.
  217. */
  218. int SHELL_Printf(shell_handle_t shellHandle, const char *formatString, ...);
  219. /*!
  220. * @brief Sends data to the shell output stream with OS synchronization.
  221. *
  222. * This function is used to send data to the shell output stream with OS synchronization, note the function could
  223. * not be called in ISR.
  224. *
  225. * @param shellHandle The shell module handle pointer.
  226. * @param buffer Start address of the data to write.
  227. * @param length Length of the data to write.
  228. * @retval kStatus_SHELL_Success Successfully send data.
  229. * @retval kStatus_SHELL_Error An error occurred.
  230. */
  231. shell_status_t SHELL_WriteSynchronization(shell_handle_t shellHandle, const char *buffer, uint32_t length);
  232. /*!
  233. * @brief Writes formatted output to the shell output stream with OS synchronization.
  234. *
  235. * Call this function to write a formatted output to the shell output stream with OS synchronization, note the
  236. * function could not be called in ISR.
  237. *
  238. * @param shellHandle The shell module handle pointer.
  239. *
  240. * @param formatString Format string.
  241. * @return Returns the number of characters printed or a negative value if an error occurs.
  242. */
  243. int SHELL_PrintfSynchronization(shell_handle_t shellHandle, const char *formatString, ...);
  244. /*!
  245. * @brief Change shell prompt.
  246. *
  247. * Call this function to change shell prompt.
  248. *
  249. * @param shellHandle The shell module handle pointer.
  250. *
  251. * @param prompt The string which will be used for command prompt
  252. * @return NULL.
  253. */
  254. void SHELL_ChangePrompt(shell_handle_t shellHandle, char *prompt);
  255. /*!
  256. * @brief Print shell prompt.
  257. *
  258. * Call this function to print shell prompt.
  259. *
  260. * @param shellHandle The shell module handle pointer.
  261. *
  262. * @return NULL.
  263. */
  264. void SHELL_PrintPrompt(shell_handle_t shellHandle);
  265. /*!
  266. * @brief The task function for Shell.
  267. * The task function for Shell; The function should be polled by upper layer.
  268. * This function does not return until Shell command exit was called.
  269. *
  270. * @param shellHandle The shell module handle pointer.
  271. */
  272. #if !(defined(SHELL_NON_BLOCKING_MODE) && (SHELL_NON_BLOCKING_MODE > 0U))
  273. void SHELL_Task(shell_handle_t shellHandle);
  274. #endif
  275. /*!
  276. * @brief Check if code is running in ISR.
  277. *
  278. * This function is used to check if code running in ISR.
  279. *
  280. * @retval TRUE if code runing in ISR.
  281. */
  282. static inline bool SHELL_checkRunningInIsr(void)
  283. {
  284. #if (defined(__DSC__) && defined(__CW__))
  285. return !(isIRQAllowed());
  286. #elif defined(__GIC_PRIO_BITS)
  287. return (0x13 == (__get_CPSR() & CPSR_M_Msk));
  288. #elif defined(__get_IPSR)
  289. return (0U != __get_IPSR());
  290. #else
  291. return false;
  292. #endif
  293. }
  294. /* @} */
  295. #if defined(__cplusplus)
  296. }
  297. #endif
  298. /*! @}*/
  299. #endif /* __FSL_SHELL_H__ */