sash - stand-alone shell with built-in commands
sash [-c command] [-f fileName ] [-p prompt] [-q] [-a]
The sash program is a stand-alone shell which is useful for
recovering from certain types of system failures. In particular, it was
created in order to cope with the problem of missing shared libraries or
important executables.
Sash can execute external programs, as in any shell. There
are no restrictions on these commands, as the standard shell is used to
execute them if there are any non-wildcard meta-characters in the
command.
More importantly, however, is that many of the standard system
commands are built-in to sash. These built-in commands are:
-ar, -chattr, -chgrp, -chmod, -chown, -chroot, -cmp,
-cp, -dd, -echo, -ed, -grep, -file, -find, -gunzip,
-gzip, -kill, -losetup, -ln, -ls, -lsattr, -mkdir,
-mknod, -more, -mount, -mv, -pivot_root, -printenv, -pwd,
-rm, -rmdir, -sum, -sync, -tar, -touch, -umount, -where
These commands are generally similar to the standard programs with
similar names. However, they are simpler and cruder than the external
programs, and so many of the options are not implemented. The restrictions
for each built-in command are described later.
The built-in commands which correspond to external programs begin
with a dash character in order to distinguish them from the external
programs. So typing "ls", for example, will attempt to run the
real ls program. If "-ls" is typed, then the built-in
command which mimics ls is called.
For the built-in commands, file names are expanded so that
asterisks, question marks, and characters inside of square brackets are
recognised and are expanded. Arguments can be quoted using single quotes,
double quotes, or backslashes. However, no other command line processing is
performed. This includes specifying of file redirection, and the specifying
of a pipeline.
If an external program is non-existant or fails to run correctly,
then the "alias" built-in command may be used to redefine the
standard command so that it automatically runs the built-in command instead.
For example, the command "alias ls -ls" redefines "ls"
to run the built-in command. This saves you the pain of having to remember
to type the leading dash all of the time. If many external programs will not
run, then the "aliasall" command may be useful to create multiple
aliases.
The "help" command will list all of the built-in
commands in sash . If an argument is given, it will list only those
built-in commands which contain the given argument as a sub-string. Each
built-in command is described below in more detail.
- alias [name
[command]]
- If name and command are provided, this defines an alias for
a command with the specified name which executes the specified command
with possible arguments. Arguments containing wildcards can be quoted in
order to defer their expansion until the alias is invoked. If just
name is provided, then the definition of the specified command
alias is displayed. If nothing is provided, then the definitions of all
aliases are displayed.
- aliasall
- This defines aliases for all of the built-in commands that start with
dashes to the corresponding names without the dashes. This may be useful
when the system is so corrupted that no external programs may be executed
at all.
- -ar [txp][v] arfile
[filename]...
- List or extract files from an ar archive. The arfile argument specifies a
file name which contains the archive. If no additional filenames are
specified, then all files in the archive are operated on. Otherwise, only
those archive members which have the same name as one of the additional
filenames are operated on. Filenames which do not appear in the archive
are ignored. Archives cannot be created or modified. The archiver
correctly handles 4.0BSD archives, and understands both the SysV and
4.4BSD extensions for long file names. The extended pseudo-BSD formats are
not supported; nor are the two antediluvian binary formats derived from V7
and earlier. (The GNU archiver normally creates archives in the 4.0BSD
format with SysV extensions.)
- cd [dirName]
- If dirName is provided, then the current directory is changed to
the dirName. If dirName is absent, then the current directory is
changed to the user's home directory (value of the $HOME environment
variable).
- -chattr [+i] [-i] [+a]
[-a] fileName ...
- Change the attributes of the specified files on an ext2 or ext3 file
system. Using a plus sign adds the specified attribute for the files.
Using a minus sign removes the specified attributes for the files. The 'i'
attribute makes a file immutable so that it cannot be changed. The 'a'
attribute makes a file append-only. This command is only available on
Linux.
- -chgrp gid fileName
...
- Change the group id for the specified list of files. The gid can
either be a group name, or a decimal value.
- -chmod mode fileName
...
- Change the mode of the specified list of files. The mode argument
can only be an octal value.
- -chown uid fileName
...
- Change the owner id for the specified list of files. The uid can
either be a user name, or a decimal value.
- -chroot
path
- Changes the root directory to that specified in path. This
directory will be used for path names beginning with /. The root directory
is inherited by all children of the current process.
- -cmp fileName1
fileName2
- Determines whether or not the specified file names have identical data.
This says that the files are links to each other, are different sizes,
differ at a particular byte number, or are identical.
- -cp srcName ...
destName
- Copies one or more files from the srcName to the destName.
If more than one srcName is given, or if destName is a directory, then all
the srcNames are copied into the destName directory with the same names as
the srcNames.
- -dd if=name of=name [bs=n]
[count=n] [skip=n] [seek=n]
- Copy data from one file to another with the specified parameters. The
if and of arguments must be provided, so stdin and stdout
cannot be specified. The bs argument is the block size, and is a
numeric value (which defaults to 512 bytes). Count is the number of
blocks to be copied (which defaults to end of file for the input file).
Skip is the number of blocks to ignore before copying (seek is used
if possible, and the default is 0). Seek is the number of blocks to
seek in the output file before writing (and defaults to 0). Any of the
numeric decimal values can have one or more trailing letters from the set
'kbw', which multiplies the value by 1024, 512, and 2 respectively. The
command reports the number of full blocks read and written, and whether or
not any partial block was read or written.
- -echo [args]
...
- Echo the arguments to the -echo command. Wildcards are expanded, so this
is a convenient way to get a quick list of file names in a directory. The
output is always terminated with a newline.
- -ed [fileName]
- Edit the specified file using line-mode commands. The following ed
commands are provided: = c r w i a d p l s f k z and q. Line numbers can
be constants, ".", "$", "'x",
/string/ and simple arithmetic combinations of these. The
substitute command and the search expression can only use literal strings.
There are some small differences in the way that some commands
behave.
- exec fileName
[args]
- Execute the specified program with the specified arguments. This replaces
sash completely by the executed program.
- exit
- Quit from sash.
- -file fileName
...
- Examine the specified files and print out their file type. This indicates
whether the files are regular files or not, whether they contain printable
text or shell scripts, are executables, or contain binary data.
- -find dirName [-xdev]
[-type chars] [-name pattern] [-size minSize]
- Find all files contained within the specified directory tree which meet
all of the specified conditions. The -xdev option prevents crossing of
mount points. The -name option specifies a wildcard pattern to match the
last component of the file names. The -type option specifies that the
files must have a type matching the specified list from the set: f d c b p
s l. These represent regular files, directories, character devices, block
devices, named pipes, sockets, and symbolic links. The -size option
specifies that the files must be regular files or directories which
contain at least the specified number of bytes.
- -grep [-in] word fileName
...
- Display lines of the specified files which contain the given word. If only
one file name is given, then only the matching lines are printed. If
multiple file names are given, then the file names are printed along with
the matching lines. Word must be a single word, (ie, not a regular
expression). If -i is given, then case is ignored when doing the search.
If -n is given, then the line numbers of the matching lines are also
printed.
- -gunzip inputFileName
... [-o outputPath]
- Uncompress one or more files that had been compressed using the
gzip or compress algorithms. If the -o option is not given,
then each of the input file names must have one of the extensions
".gz", ".tgz", or ".Z", and those files will
be replaced by the uncompressed versions of those files. The original
files will be deleted after the output files have been successfully
created. The uncompressed versions of the files have the same names as the
original file names, except for a simple modification of their extensions.
If an extension is ".tgz", then the extension is replaced by
".tar". Otherwise, the ".gz" or ".Z"
extension is removed.
If the -o option is given, then the input files will not be
deleted, and the uncompressed versions of the files will be created as
specified by outputPath. If the output path is a directory, then
the uncompressed versions of the input files will be placed in that
directory with their file names modified as described above, or with the
same name if the input file name does not have one of the special
extensions. If the output path is a regular file, then only one input
file is allowed, and the uncompressed version of that input file is
created as the output path exactly as specified. If the output path is a
block or character device, then the uncompressed versions of the input
files are concatenated to the device.
This command is only available if sash was compiled to
use the gzip library.
- -gzip inputFileName ... [-o
outputPath]
- Compresses one or more files using the gzip algorithm. If the -o
option is not given, then each of the input file names will be replaced by
the compressed versions of those files, The original files will be deleted
after the output files have been successfully created. The compressed
versions of the files have the same names as the original file names,
except for a simple modification of the extensions. If an extension is
".tar", then the extension is replaced by ".tgz".
Otherwise, the ".gz" extension is added.
If the -o option is given, then the input files will not be
deleted, and the compressed versions of the files will be created as
specified by outputPath. If the output path is a directory, then
the compressed versions of the input files will be placed in that
directory with their file names modified as described above. If the
output path is not a directory, then only one input file is allowed, and
the compressed version of that input file is created as the output path
exactly as specified.
This command is only available if sash was compiled to
use the gzip library.
- help [word]
- Displays a list of built-in commands along with their usage strings. If a
word is given, then just those commands whose name or usage contains the
word is displayed. If a word is specified which exactly matches a built-in
command name, then a short description of the command and its usage is
given.
- -kill [-signal] pid
...
- Sends the specified signal to the specified list of processes.
Signal is a numeric value, or one of the special values HUP, INT,
QUIT, KILL, TERM, STOP, CONT, USR1 or USR2. If no signal is specified then
SIGTERM is used.
- -losetup [-d] loopDev
[file]
- Associates loopback devices with files on the system. If -d is not
given, the loopback device loopDev is associated with file.
If -d is given, loopDev is unassociated with the file it's
currently configured for.
- -ln [-s] srcName ...
destName
- Links one or more files from the srcName to the specified
destName. If there are multiple srcNames, or destName is a
directory, then the link is put in the destName directory with the same
name as the source name. The default links are hard links. Using -s makes
symbolic links. For symbolic links, only one srcName can be
specified.
- -ls [-lidFC] fileName
...
- Display information about the specified list of file names. The normal
listing is simply a list of file names, one per line. The options
available are -l, -n, -i, -d, and -F. The -l option produces a long
listing giving the normal 'ls' information. The -n option is like -l
except that numeric user and group ids are shown. The -i option displays
the inode numbers of the files. The -d option displays information about a
directory, instead of the files within it. The -F option appends a slash
or asterisk to the file name if the file is a directory or is executable.
The -C option displays the file names in a multi-column format. The width
of the output is calculated using the COLS environment variable.
- -lsattr fileName
...
- Display attributes for the specified files on an ext2 or ext3 file system.
The letter 'i' indicates that the file is immutable and cannot change. The
letter 'a' indicates that the file is append-only. Dashes are shown where
the attributes are not set. This command is only available on Linux.
- -mkdir dirName
...
- Creates the specified directories. They are created with the default
permissions.
- -mknod fileName type
major minor
- Creates a special device node, either a character file or a block file.
Filename is the name of the node. Type is either 'c' or 'd'.
Major is the major device number. Minor is the minor device
number. Both of these numbers are decimal.
- -more fileName
...
- Type out the contents of the specified file names, one page at a time. For
each page displayed, you can type 'n' and a return to go to the next file,
'q' and a return to quit the command completely, or just a return to go to
the next page. The environment variables LINES and COLS can be used to set
the page size.
- -mount [-t type] [-r]
[-s] [-e] [-m] devName dirName
- Mount a filesystem on a directory name. The -t option specifies the type
of filesystem being mounted, and defaults to "ext3" for Linux
and "ffs" for BSD. The -r option indicates to mount the
filesystem read-only. The -s option indicates to mount the filesystem
no-suid. The -e option indicates to mount the filesystem no-exec. The -m
option indicates to remount an already mounted filesystem. The -m option
is only available on Linux.
- -mv srcName ...
destName
- Moves one or more files from the srcName to the destName. If
multiple srcNames are given, or if destName is a directory, then the
srcNames are copied into the destination directory with the same names as
the srcNames. Renames are attempted first, but if this fails because of
the files being on different filesystems, then copies and deletes are done
instead.
- -pivot_root
newRoot putOld
- Moves the root file system of the current process to the directory
putOld and makes newRoot the new root file system of the
current process.
- -printenv
[name]
- If name is not given, this prints out the values of all the current
environment variables. If name is given, then only that environment
variable value is printed.
- prompt [word]
...
- Sets the prompt string that is displayed before reading of a command. A
space is always added to the specified prompt.
- -pwd
- Prints the current working directory.
- quit
- Exits from sash.
- -rm fileName ...
- Removes one or more files.
- -rmdir dirName
...
- Removes one or more directories. The directories must be empty for this to
be successful.
- setenv name
value
- Set the value of an environment variable.
- source
fileName
- Execute commands which are contained in the specified file name.
- -sum fileName
...
- Calculates checksums for one or more files. This is the 16 bit checksum
compatible with the BSD sum program.
- -sync
- Do a "sync" system call to force dirty blocks out to the
disk.
- -tar [ctxv]f tarFileName
[fileName] ...
- Create, list or extract files from a tar archive. The f option must be
specified, and accepts a device or file name argument which contains the
tar archive. When creating, at least one file name must be specified to be
stored. If a file name is a directory, then all the files and directories
within the directory are stored. Linked files and other special file types
are not handled properly. When listing or extracting files, only those
files starting with the specified file names are processed. If no file
names are specified, then all files in the archive are processed. Leading
slashes in the tar archive file names are always removed so that you might
need to cd to "/" to restore files which had absolute
paths.
- -touch fileName
...
- Updates the modify times of the specifed files. If a file does not exist,
then it will be created with the default protection.
- umask [mask]
- If mask is given, sets the "umask" value used for
initializing the permissions of newly created files. If mask is not
given, then the current umask value is printed. The mask is an octal
value.
- -umount [-f]
fileName
- Unmounts a file system. The file name can either be the device name which
is mounted, or else the directory name which the file system is mounted
onto. The -f option unmounts the filesystem even if it is being used. The
-f option is only available on BSD.
- unalias
name
- Remove the definition for the specified alias.
- -where
program
- Prints out all of paths defined by the PATH environment variable where the
specified program exists. If the program exists but cannot be executed,
then the reason is also printed.
There are several command line options to sash.
The -c option executes the next argument as a command (including
embedded spaces to separate the arguments of the command), and then
exits.
The -f option executes the commands contained in the file name
specified by the next argument, and then exits. This feature can be used to
create executable scripts for sash by starting the script file with a
line similar to:
#! /bin/sash -f
The -p option takes the next argument as the prompt string to be
used when prompting for commands.
The -q option makes sash quiet, which simply means that it
doesn't print its introduction line when it starts. This option is also
implied if the -c or -f options are used.
The -a option creates aliases for the built-in commands so that
they replace the corresponding standard commands. This is the same result as
if the 'aliasall' command was used.
This section contains some useful information about using
sash with lilo to perform system recovery in some situations.
Similar concepts should exist for other boot loaders and operating
systems.
When important shared libraries are being upgraded, it might be a
good idea to have sash already running on a console by itself. Then
if there is a problem with the shared libraries sash will be
unaffected and you may be able to use it to fix the problem.
If a problem with the system shows up at boot time so that you
cannot enter multi-user mode and log in, then you can first try booting into
single-user mode by adding the single keyword after your kernel image
name at the lilo prompt. If you manage to reach a shell prompt, then
you can run sash from that shell (if necessary). One reason for doing
this is that you might need to use the -mount command with the -m
option to remount the root file system so that it can be modified.
If you cannot reach the shell in single-user mode, then you can
try running sash directly as a replacement for the init process. This is
done by adding the init=/bin/sash keyword after your kernel image
name at the lilo prompt. When this is done, then the use of the
aliasall command might be useful to reduce attempts to access the
root file system when running commands.
If your root file system is so corrupted that you cannot get
sash to run at all, then you will have to resort to a system recovery
floppy.
Sash should obviously be linked statically, otherwise its
purpose is lost. Note that even if the rest of the program is linked
statically, the password and group lookup routines in the C library can
still be dynamic. For that reason, if there are problems then it might be
necessary to only use numeric ids for the -chown and -chgrp commands and to
use the -n option instead of -l for the -ls command.
Several other system commands might be necessary for system
recovery, but aren't built-in to sash.
David I. Bell
dbell@tip.net.au
5 March 2014