--- cpukit/libmisc/Makefile.am | 3 + cpukit/libmisc/shell/main_cmdchmod.c | 85 ++++++++++++++++ cpukit/libmisc/shell/main_cmdchown.c | 106 ++++++++++++++++++++ cpukit/libmisc/shell/main_cmdls.c | 91 +++++++++++++++++ cpukit/libmisc/shell/shellconfig.h | 18 ++++ doc/shell/general.t | 186 +++++++++++++++++++++++++++++++++++ 6 files changed, 489 insertions(+) create mode 100644 cpukit/libmisc/shell/main_cmdchmod.c create mode 100644 cpukit/libmisc/shell/main_cmdchown.c create mode 100644 cpukit/libmisc/shell/main_cmdls.c
diff --git a/cpukit/libmisc/Makefile.am b/cpukit/libmisc/Makefile.am index 021a251..0cc9851 100644 --- a/cpukit/libmisc/Makefile.am +++ b/cpukit/libmisc/Makefile.am @@ -112,6 +112,9 @@ libshell_a_SOURCES = shell/cat_file.c shell/cmds.c shell/internal.h \ shell/main_lsof.c shell/main_edit.c \ shell/main_blkstats.c \ shell/shell-wait-for-input.c +libshell_a_SOURCES += shell/main_cmdls.c +libshell_a_SOURCES += shell/main_cmdchown.c +libshell_a_SOURCES += shell/main_cmdchmod.c if LIBNETWORKING libshell_a_SOURCES += \ diff --git a/cpukit/libmisc/shell/main_cmdchmod.c b/cpukit/libmisc/shell/main_cmdchmod.c new file mode 100644 index 0000000..ea125fd --- /dev/null +++ b/cpukit/libmisc/shell/main_cmdchmod.c @@ -0,0 +1,85 @@ +/* + * Copyright (c) 2014 embedded brains GmbH. All rights reserved. + * + * embedded brains GmbH + * Dornierstr. 4 + * 82178 Puchheim + * Germany + * <rt...@embedded-brains.de> + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * http://www.rtems.org/license/LICENSE. + */ + +#if HAVE_CONFIG_H + #include "config.h" +#endif + +#include <errno.h> +#include <stdio.h> +#include <string.h> +#include <unistd.h> + +#include <rtems/shellconfig.h> +#include <rtems/stringto.h> + +#include "internal.h" + +static int usage(void) +{ + puts(rtems_shell_CMDCHMOD_Command.usage); + + return -1; +} + +static void error(const char *s, int eno) +{ + printf("%s: %s\n", s, strerror(eno)); +} + +static int rtems_shell_main_cmdchmod(int argc, char **argv) +{ + if (argc >= 2) { + unsigned long mode; + rtems_status_code sc; + uid_t task_uid; + int i; + + sc = rtems_string_to_unsigned_long(argv[1], &mode, NULL, 8); + if (sc != RTEMS_SUCCESSFUL) { + return usage(); + } + + task_uid = getuid(); + + for (i = 2; i < argc; ++i) { + const char *cmd = argv[i]; + rtems_shell_cmd_t *shell_cmd = rtems_shell_lookup_cmd(cmd); + + if (shell_cmd != NULL) { + if (task_uid == 0 || task_uid == shell_cmd->uid) { + shell_cmd->mode = mode + & (S_IRUSR | S_IXUSR | S_IRGRP | S_IXGRP | S_IROTH | S_IXOTH); + } else if (rtems_shell_can_see_cmd(shell_cmd)) { + error(cmd, EACCES); + } else { + error(cmd, ENOENT); + } + } else { + error(cmd, ENOENT); + } + } + } else { + return usage(); + } + + return 0; +} + +rtems_shell_cmd_t rtems_shell_CMDCHMOD_Command = { + .name = "cmdchmod", + .usage = "cmdchmod OCTAL-MODE COMMAND...", + .topic = "misc", + .command = rtems_shell_main_cmdchmod +}; diff --git a/cpukit/libmisc/shell/main_cmdchown.c b/cpukit/libmisc/shell/main_cmdchown.c new file mode 100644 index 0000000..9cc8c44 --- /dev/null +++ b/cpukit/libmisc/shell/main_cmdchown.c @@ -0,0 +1,106 @@ +/* + * Copyright (c) 2014 embedded brains GmbH. All rights reserved. + * + * embedded brains GmbH + * Dornierstr. 4 + * 82178 Puchheim + * Germany + * <rt...@embedded-brains.de> + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * http://www.rtems.org/license/LICENSE. + */ + +#if HAVE_CONFIG_H + #include "config.h" +#endif + +#include <errno.h> +#include <stdio.h> +#include <string.h> +#include <unistd.h> + +#include <rtems/shellconfig.h> + +#include "internal.h" + +static int usage(void) +{ + puts(rtems_shell_CMDCHOWN_Command.usage); + + return -1; +} + +static void error(const char *s, int eno) +{ + printf("%s: %s\n", s, strerror(eno)); +} + +static int rtems_shell_main_cmdchown(int argc, char **argv) +{ + if (argc >= 2) { + const char *s = argv[1]; + unsigned new_uid = UINT_MAX; + unsigned new_gid = UINT_MAX; + bool change_uid = false; + bool change_gid = false; + uid_t task_uid; + int i; + + if (strcmp(s, ":") != 0) { + int n = sscanf(argv[1], "%u:%u", &new_uid, &new_gid); + + if (n == 2) { + change_uid = true; + change_gid = true; + } else if (n == 1) { + change_uid = true; + } else { + n = sscanf(argv[1], ":%u", &new_gid); + + if (n == 1) { + change_gid = true; + } else { + return usage(); + } + } + } + + task_uid = getuid(); + + for (i = 2; i < argc; ++i) { + const char *cmd = argv[i]; + rtems_shell_cmd_t *shell_cmd = rtems_shell_lookup_cmd(cmd); + + if (shell_cmd != NULL) { + if (task_uid == 0 || task_uid == shell_cmd->uid) { + if (change_uid) { + shell_cmd->uid = new_uid; + } + + if (change_gid) { + shell_cmd->gid = new_gid; + } + } else if (rtems_shell_can_see_cmd(shell_cmd)) { + error(cmd, EACCES); + } else { + error(cmd, ENOENT); + } + } else { + error(cmd, ENOENT); + } + } + } else { + return usage(); + } + + return 0; +} + +rtems_shell_cmd_t rtems_shell_CMDCHOWN_Command = { + .name = "cmdchown", + .usage = "cmdchown [OWNER][:[GROUP]] COMMAND...", + .topic = "misc", + .command = rtems_shell_main_cmdchown +}; diff --git a/cpukit/libmisc/shell/main_cmdls.c b/cpukit/libmisc/shell/main_cmdls.c new file mode 100644 index 0000000..f08925c --- /dev/null +++ b/cpukit/libmisc/shell/main_cmdls.c @@ -0,0 +1,91 @@ +/* + * Copyright (c) 2014 embedded brains GmbH. All rights reserved. + * + * embedded brains GmbH + * Dornierstr. 4 + * 82178 Puchheim + * Germany + * <rt...@embedded-brains.de> + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * http://www.rtems.org/license/LICENSE. + */ + +#if HAVE_CONFIG_H + #include "config.h" +#endif + +#include <errno.h> +#include <stdio.h> +#include <string.h> + +#include <rtems/shellconfig.h> + +#include "internal.h" + +static void error(const char *s, int eno) +{ + printf("%s: %s\n", s, strerror(eno)); +} + +static void print_cmd(const rtems_shell_cmd_t *shell_cmd) +{ + if (rtems_shell_can_see_cmd(shell_cmd)) { + mode_t m = shell_cmd->mode; + + printf( + "%c%c%c%c%c%c%c%c%c %5u %5u %s\n", + (m & S_IRUSR) != 0 ? 'r' : '-', + (m & S_IWUSR) != 0 ? 'w' : '-', + (m & S_IXUSR) != 0 ? 'x' : '-', + (m & S_IRGRP) != 0 ? 'r' : '-', + (m & S_IWGRP) != 0 ? 'w' : '-', + (m & S_IXGRP) != 0 ? 'x' : '-', + (m & S_IROTH) != 0 ? 'r' : '-', + (m & S_IWOTH) != 0 ? 'w' : '-', + (m & S_IXOTH) != 0 ? 'x' : '-', + (unsigned) shell_cmd->uid, + (unsigned) shell_cmd->gid, + shell_cmd->name + ); + } +} + +static int rtems_shell_main_cmdls(int argc, char **argv) +{ + const rtems_shell_cmd_t *shell_cmd; + + if (argc <= 1) { + shell_cmd = rtems_shell_first_cmd; + + while (shell_cmd != NULL) { + print_cmd(shell_cmd); + + shell_cmd = shell_cmd->next; + } + } else { + int i; + + for (i = 1; i < argc; ++i) { + const char *cmd = argv[i]; + + shell_cmd = rtems_shell_lookup_cmd(cmd); + + if (shell_cmd != NULL) { + print_cmd(shell_cmd); + } else { + error(cmd, ENOENT); + } + } + } + + return 0; +} + +rtems_shell_cmd_t rtems_shell_CMDLS_Command = { + .name = "cmdls", + .usage = "cmdls COMMAND...", + .topic = "misc", + .command = rtems_shell_main_cmdls +}; diff --git a/cpukit/libmisc/shell/shellconfig.h b/cpukit/libmisc/shell/shellconfig.h index c5fced3..cc2165b 100644 --- a/cpukit/libmisc/shell/shellconfig.h +++ b/cpukit/libmisc/shell/shellconfig.h @@ -24,6 +24,9 @@ extern rtems_shell_cmd_t rtems_shell_HELP_Command; extern rtems_shell_cmd_t rtems_shell_ALIAS_Command; extern rtems_shell_cmd_t rtems_shell_TIME_Command; +extern rtems_shell_cmd_t rtems_shell_CMDLS_Command; +extern rtems_shell_cmd_t rtems_shell_CMDCHOWN_Command; +extern rtems_shell_cmd_t rtems_shell_CMDCHMOD_Command; extern rtems_shell_cmd_t rtems_shell_LOGOFF_Command; extern rtems_shell_cmd_t rtems_shell_SETENV_Command; extern rtems_shell_cmd_t rtems_shell_GETENV_Command; @@ -162,6 +165,21 @@ extern rtems_shell_alias_t * const rtems_shell_Initial_aliases[]; * Common commands that can be optional */ #if (defined(CONFIGURE_SHELL_COMMANDS_ALL) && \ + !defined(CONFIGURE_SHELL_NO_COMMAND_CMDLS)) || \ + defined(CONFIGURE_SHELL_COMMAND_CMDLS) + &rtems_shell_CMDLS_Command, + #endif + #if (defined(CONFIGURE_SHELL_COMMANDS_ALL) && \ + !defined(CONFIGURE_SHELL_NO_COMMAND_CMDCHOWN)) || \ + defined(CONFIGURE_SHELL_COMMAND_CMDCHOWN) + &rtems_shell_CMDCHOWN_Command, + #endif + #if (defined(CONFIGURE_SHELL_COMMANDS_ALL) && \ + !defined(CONFIGURE_SHELL_NO_COMMAND_CMDCHMOD)) || \ + defined(CONFIGURE_SHELL_COMMAND_CMDCHMOD) + &rtems_shell_CMDCHMOD_Command, + #endif + #if (defined(CONFIGURE_SHELL_COMMANDS_ALL) && \ !defined(CONFIGURE_SHELL_NO_COMMAND_JOEL)) || \ defined(CONFIGURE_SHELL_COMMAND_JOEL) &rtems_shell_JOEL_Command, diff --git a/doc/shell/general.t b/doc/shell/general.t index c0df5c1..ce8a5bb 100644 --- a/doc/shell/general.t +++ b/doc/shell/general.t @@ -13,6 +13,9 @@ The RTEMS shell has the following general commands: @item @code{help} - Print command help @item @code{alias} - Add alias for an existing command +@item @code{cmdls} - List commands +@item @code{cmdchown} - Change user or owner of commands +@item @code{cmdchmod} - Change mode of commands @item @code{date} - Print or set current date and time @item @code{echo} - Produce message in a shell script @item @code{sleep} - Delay for a specified amount of time @@ -196,6 +199,189 @@ extern rtems_shell_cmd_t rtems_shell_ALIAS_Command; @c @c @page +@subsection cmdls - List commands + +@pgindex cmdls + +@subheading SYNOPSYS: + +@example +cmdls COMMAND... +@end example + +@subheading DESCRIPTION: + +This command lists the visible commands of the command set. + +@subheading EXIT STATUS: + +This command returns 0 on success and non-zero if an error is encountered. + +@subheading NOTES: + +The current user must have read permission to list a command. + +@subheading EXAMPLES: + +The following is an example of how to use @code{cmdls}: + +@example +SHLL [/] # cmdls help shutdown +r-xr-xr-x 0 0 help +r-x------ 0 0 shutdown +@end example + +@subheading CONFIGURATION: + +@findex CONFIGURE_SHELL_NO_COMMAND_CMDLS +@findex CONFIGURE_SHELL_COMMAND_CMDLS + +This command is included in the default shell command set. +When building a custom command set, define +@code{CONFIGURE_SHELL_COMMAND_CMDLS} to have this +command included. + +This command can be excluded from the shell command set by +defining @code{CONFIGURE_SHELL_NO_COMMAND_CMDLS} when all +shell commands have been configured. + +@subheading PROGRAMMING INFORMATION: + +The configuration structure for the @code{cmdls} has the +following prototype: + +@example +extern rtems_shell_cmd_t rtems_shell_CMDLS_Command; +@end example + +@c +@c +@c +@page +@subsection cmdchown - Change user or owner of commands + +@pgindex cmdchown + +@subheading SYNOPSYS: + +@example +cmdchown [OWNER][:[GROUP]] COMMAND... +@end example + +@subheading DESCRIPTION: + +This command changes the user or owner of a command. + +@subheading EXIT STATUS: + +This command returns 0 on success and non-zero if an error is encountered. + +@subheading NOTES: + +The current user must have an UID of zero or be the command owner to change the +owner or group. + +@subheading EXAMPLES: + +The following is an example of how to use @code{cmdchown}: + +@example +[/] # cmdls help +r-xr-xr-x 0 0 help +[/] # cmdchown 1:1 help +[/] # cmdls help +r--r--r-- 1 1 help +@end example + +@subheading CONFIGURATION: + +@findex CONFIGURE_SHELL_NO_COMMAND_CMDCHOWN +@findex CONFIGURE_SHELL_COMMAND_CMDCHOWN + +This command is included in the default shell command set. +When building a custom command set, define +@code{CONFIGURE_SHELL_COMMAND_CMDCHOWN} to have this +command included. + +This command can be excluded from the shell command set by +defining @code{CONFIGURE_SHELL_NO_COMMAND_CMDCHOWN} when all +shell commands have been configured. + +@subheading PROGRAMMING INFORMATION: + +The configuration structure for the @code{cmdchown} has the +following prototype: + +@example +extern rtems_shell_cmd_t rtems_shell_CMDCHOWN_Command; +@end example + +@c +@c +@c +@page +@subsection cmdchmod - Change mode of commands + +@pgindex cmdchmod + +@subheading SYNOPSYS: + +@example +cmdchmod OCTAL-MODE COMMAND... +@end example + +@subheading DESCRIPTION: + +This command changes the mode of a command. + +@subheading EXIT STATUS: + +This command returns 0 on success and non-zero if an error is encountered. + +@subheading NOTES: + +The current user must have an UID of zero or be the command owner to change the +mode. + +@subheading EXAMPLES: + +The following is an example of how to use @code{cmdchmod}: + +@example +[/] # cmdls help +r-xr-xr-x 0 0 help +[/] # cmdchmod 544 help +[/] # cmdls help +r-xr--r-- 0 0 help +@end example + +@subheading CONFIGURATION: + +@findex CONFIGURE_SHELL_NO_COMMAND_CMDCHMOD +@findex CONFIGURE_SHELL_COMMAND_CMDCHMOD + +This command is included in the default shell command set. +When building a custom command set, define +@code{CONFIGURE_SHELL_COMMAND_CMDCHMOD} to have this +command included. + +This command can be excluded from the shell command set by +defining @code{CONFIGURE_SHELL_NO_COMMAND_CMDCHMOD} when all +shell commands have been configured. + +@subheading PROGRAMMING INFORMATION: + +The configuration structure for the @code{cmdchmod} has the +following prototype: + +@example +extern rtems_shell_cmd_t rtems_shell_CMDCHMOD_Command; +@end example + +@c +@c +@c +@page @subsection date - print or set current date and time @pgindex date -- 1.8.4.5 _______________________________________________ devel mailing list devel@rtems.org http://lists.rtems.org/mailman/listinfo/devel