diff --git a/doc/reference/shell/images/dict_cmd.png b/doc/reference/shell/images/dict_cmd.png new file mode 100644 index 00000000000..b5670b1cad6 Binary files /dev/null and b/doc/reference/shell/images/dict_cmd.png differ diff --git a/doc/reference/shell/index.rst b/doc/reference/shell/index.rst index 05f519d27ce..477dfa8a349 100644 --- a/doc/reference/shell/index.rst +++ b/doc/reference/shell/index.rst @@ -17,6 +17,7 @@ interaction is required. This module is a Unix-like shell with these features: * Support for multiple instances. * Advanced cooperation with the :ref:`logging_api`. * Support for static and dynamic commands. +* Support for dictionary commands. * Smart command completion with the :kbd:`Tab` key. * Built-in commands: :command:`clear`, :command:`shell`, :command:`colors`, :command:`echo`, :command:`history` and :command:`resize`. @@ -34,8 +35,11 @@ interaction is required. This module is a Unix-like shell with these features: The module can be connected to any transport for command input and output. At this point, the following transport layers are implemented: -* UART * Segger RTT +* SMP +* Telnet +* UART +* USB * DUMMY - not a physical transport layer Connecting to Segger RTT via TCP (on macOS, for example) @@ -75,6 +79,7 @@ types: * Dynamic subcommand (level > 0): Number and syntax does not need to be known during compile time. Created in the software module. + Creating commands ================= @@ -100,6 +105,8 @@ Use the following macros for adding shell commands: time expression is non-zero. * :c:macro:`SHELL_STATIC_SUBCMD_SET_CREATE` - Create a static subcommands array. +* :c:macro:`SHELL_SUBCMD_DICT_SET_CREATE` - Create a dictionary subcommands + array. * :c:macro:`SHELL_DYNAMIC_CMD_CREATE` - Create a dynamic subcommands array. Commands can be created in any file in the system that includes @@ -131,6 +138,52 @@ subcommands. Example implementation can be found under following location: :zephyr_file:`samples/subsys/shell/shell_module/src/main.c`. +Dictionary commands +=================== +This is a special kind of static commands. Dictionary commands can be used +every time you want to use a pair: (string <-> corresponding data) in +a command handler. The string is usually a verbal description of a given data. +The idea is to use the string as a command syntax that can be prompted by the +shell and corresponding data can be used to process the command. + +Let's use an example. Suppose you created a command to set an ADC gain. +It is a perfect place where a dictionary can be used. The dictionary would +be a set of pairs: (string: gain_value, int: value) where int value could +be used with the ADC driver API. + +Abstract code for this task would look like this: + +.. code-block:: c + + static int gain_cmd_handler(const struct shell *shell, + size_t argc, char **argv, void *data) + { + int gain; + + /* data is a value corresponding to called command syntax */ + gain = (int)data; + adc_set_gain(gain); + + shell_print(shell, "ADC gain set to: %s\n" + "Value send to ADC driver: %d", + argv[0], + gain); + + return 0; + } + + SHELL_SUBCMD_DICT_SET_CREATE(sub_gain, gain_cmd_handler, + (gain_1, 1), (gain_2, 2), (gain_1_2, 3), (gain_1_4, 4) + ); + SHELL_CMD_REGISTER(gain, &sub_gain, "Set ADC gain", NULL); + + +This is how it would look like in the shell: + +.. image:: images/dict_cmd.png + :align: center + :alt: Dictionary commands example. + Dynamic commands ---------------- diff --git a/include/shell/shell.h b/include/shell/shell.h index 729627133b0..7db6eba3b53 100644 --- a/include/shell/shell.h +++ b/include/shell/shell.h @@ -429,22 +429,28 @@ static int UTIL_CAT(cmd_dict_, GET_ARG_N(1, __DEBRACKET _data))( \ /** * @brief Initializes shell dictionary commands. * + * This is a special kind of static commands. Dictionary commands can be used + * every time you want to use a pair: (string <-> corresponding data) in + * a command handler. The string is usually a verbal description of a given + * data. The idea is to use the string as a command syntax that can be prompted + * by the shell and corresponding data can be used to process the command. + * * @param[in] _name Name of the dictionary subcommand set * @param[in] _handler Command handler common for all dictionary commands. - * @see shell_dict_cmd_handler + * @see shell_dict_cmd_handler * @param[in] ... Dictionary pairs: (command_syntax, value). Value will be - * passed to the _handler as user data. + * passed to the _handler as user data. * * Example usage: * static int my_handler(const struct shell *shell, * size_t argc, char **argv, void *data) * { * int val = (int)data; - + * * shell_print(shell, "(syntax, value) : (%s, %d)", argv[0], val); * return 0; * } - + * * SHELL_SUBCMD_DICT_SET_CREATE(sub_dict_cmds, my_handler, * (value_0, 0), (value_1, 1), (value_2, 2), (value_3, 3) * );