| Both sides previous revisionPrevious revisionNext revision | Previous revision |
| shell [February 09, 2026 at 20:37] – yanevskiv | shell [May 14, 2026 at 13:07] (current) – yanevskiv |
|---|
| | # Shell |
| | ## What is a shell? |
| | **Shell** is a program that lets you to run other programs in the terminal. |
| | |
| | Shell allows you to pass command line arguments, set environment variables and redirect the program's stardard input / output / error. It allows you to chain programs, such that output from one program is redirected as input to another program. It also allows you to run the programs in the background. Basically, a shell allows you to easily orchestrate programs in the terminal. |
| | |
| | When people say "run this command in a terminal" they usually mean running the command in a terminal shell. Any program (like vim) can theoretically run in the terminal on its own, without being started by a shell. But -- it is the shell that allows you to type in `vim file.txt` and hit enter to run vim. The shell is the one that parses that and says "Aha, the user wants to run the program `/usr/bin/vim` and pass `file.txt` as the only argument". |
| | |
| | The most popular shell in [[gnu-linux|GNU/Linux]] is bash shell. |
| | |
| | ## Command line |
| | When you open an interactive shell, you are given a command line. You run commands by typing them in the command line and hitting Enter. Command line arguments are given after the command, separated by any number of whitespaces (either spaces or tabs). |
| | |
| | The part at the beginning is called a 'prompt'. It usually lists your user, hostname, and current working directory. In this case, user is 'root', hostname is 'localhost', and current working directory is '~' i.e. home directory of root user (which is `/root`). These are enclosed withing '[' and ']' characters just for decoration. The last character '#' separates the prompt from the command you're typing. Usually, the separator `#` indicates the user is root (as is the case here), while `$` indicates the user is a regular user. |
| | ``` |
| | [root@localhost ~]# |
| | ``` |
| | |
| | The shell offers environment variables for the information that's displayed in the prompt: `$USER` for user, `$HOSTNAME` for hostname, and `$PWD` for current working directory. The prompt itself is defined by `$PS1` variable which stands for 'Prompt String 1'. You can inspect these you can use the `echo` or `printf` commands: |
| | |
| | ``` |
| | [root@localhost ~]# echo $USER |
| | root |
| | |
| | [root@localhost ~]# echo $HOSTNAME |
| | localhost |
| | |
| | [root@localhost ~]# echo $PWD |
| | /root |
| | |
| | [root@localhost ~]# echo $PS1 |
| | [\u@\h \W]\$ |
| | ``` |
| | |
| | ## Basic commands |
| | The four basic shell commands listed in this section are `cd`, `ls`, `echo`, and `cat`. These are your legs, eyes, mouth, and ears, while you navigate the filesystem forest. |
| | |
| | ### cd |
| | The `cd` command stands for "Change directory". It's used to change the current working directory a.k.a. `$PWD`. You supply where you want to go with the argument e.g. `cd /usr/bin`. The cd command always expects a single argument. If your path has a space for example, you will have to enclose the path in quotation marks like `cd "/home/user/directory with space"`. If you don't supply any arguments it will put you in `$HOME` directory. Many shells support `cd -` which undoes the movement in case you go somewhere you didn't want by mistake. |
| | |
| | The `cd` command doesn't print anything upon success. This follows the Unix philosophy of "no news is good news" -- meaning if there is no feedback then everything went fine. If you try to navigate to a non-existing directory like `cd /fdsa/fdsa/fdsa` then you'll likely get some feedback that the path doesn't exist. |
| | ``` |
| | [root@localhost ~]# cd /usr/bin |
| | ``` |
| | |
| | ### ls |
| | The `ls` command stands for "List". It's used to list files in a directory. Commonly, you use it without arguments in order to list files in `$PWD` (i.e. the current working directory). Some common arguments are `la -a`, and `la -l`. |
| | |
| | The `ls -a` option stands for "all" . It will include hidden files, which are just files which start with a dot, like `.hidden`. There is no special way to "hide" files in Unix filesystems like there is on Windows, so a convention was a established to just treat files that start with a dot as "hidden". Configuration files in your `$HOME` directory often start with a dot. This is why configuration files are also commonly called "dotfiles". |
| | |
| | The `ls -l` option stands for "long". It will include a detailed table that lists files line by line, including permissions, owner, group, size (in bytes), modification date, file name, ... |
| | |
| | To provide both `-a` and `-l` at the same time, you commonly slug them together like `ls -la`. There is really no difference between `ls -l -a` or `ls -la`. |
| | |
| | |
| | ``` |
| | [root@localhost ~]# ls / |
| | bin boot dev etc home lib lib64 mnt opt proc root run sbin srv sys tmp usr var |
| | |
| | [root@ivan-darwin /]# ls -la / |
| | total 20 |
| | drwxr-xr-x 1 root root 142 Jan 31 21:31 . |
| | drwxr-xr-x 1 root root 142 Jan 31 21:31 .. |
| | lrwxrwxrwx 1 root root 7 Oct 12 18:21 bin -> usr/bin |
| | drwxr-xr-x 6 root root 4096 Jan 1 1970 boot |
| | drwxr-xr-x 23 root root 4480 Feb 9 12:39 dev |
| | drwxr-xr-x 1 root root 3100 Feb 8 00:38 etc |
| | drwxr-xr-x 1 root root 58 Feb 1 00:19 home |
| | lrwxrwxrwx 1 root root 7 Oct 12 18:21 lib -> usr/lib |
| | lrwxrwxrwx 1 root root 7 Oct 12 18:21 lib64 -> usr/lib |
| | drwxr-xr-x 1 root root 0 Oct 12 18:21 mnt |
| | drwxr-xr-x 1 root root 184 Feb 1 01:11 opt |
| | dr-xr-xr-x 446 root root 0 Feb 9 09:11 proc |
| | drwx------ 1 root root 70 Jan 31 23:03 root |
| | drwxr-xr-x 30 root root 760 Feb 9 14:22 run |
| | lrwxrwxrwx 1 root root 7 Oct 12 18:21 sbin -> usr/bin |
| | drwxr-x--- 1 root root 2 Jan 31 21:40 .snapshots |
| | drwxr-xr-x 1 root root 14 Jan 31 21:30 srv |
| | dr-xr-xr-x 13 root root 0 Feb 9 13:13 sys |
| | drwxrwxrwt 17 root root 400 Feb 9 14:15 tmp |
| | drwxr-xr-x 1 root root 80 Feb 4 15:13 usr |
| | drwxr-xr-x 1 root root 116 Feb 4 15:30 var |
| | ``` |
| | |
| | ### echo |
| | The `echo` command is named after the [echo phenomenon](https://en.wikipedia.org/wiki/Echo). The command just echoes back to you whatever you say. The utility of the command is that shell commn |
| | ``` |
| | [root@localhost ~]# echo $HOME |
| | /root |
| | |
| | [root@localhost ~]# echo Hello World |
| | Hello World |
| | ``` |
| | |
| | ### cat |
| | |
| | ## Command arguments |
| | |
| | |
| | ```c |
| | // Compile: gcc main.c -o main |
| | // Execute: ./main |
| | |
| | #include <stdio.h> |
| | int main(int argc, char *argv[]) |
| | { |
| | printf("argc = %d\n", argc); |
| | for (int i = 0; i < argc; i++) { |
| | printf("argv[i] = %s\n", argv[i]); |
| | } |
| | } |
| | ``` |
| | |
| | |
| | ## Internal / external commands |
| | Some commands are internal, while most commands are external. |
| | |
| | Internal commands are part of the shell itself. These are commands like `cd`, `pushd`, `popd`, `jobs`, `fg`, `bg`, `ulimit`, `shopt`. They affect the shell in some way e.g. the current working directory. |
| | |
| | External commands are actual programs. These are commands like `ls`, `cat`, `grep`, `sed`, `awk`. When you run external commands the shell looks at the `$PATH` variable. Usually `/bin`, `/usr/bin`, `~/.local/bin`. |
| | |
| | In practice, there is little to no difference between internal and external commands. However internal commands don't usually have their own manpage. E.g. there is no `man cd`. The manual for internal commands is usually given in the man page of the shell e.g. `man bash` for Bash shell. External commands are independent programs and thus usually come with their own man pages (sometimes even multiple man pages!) |
| | |
| | |
| | ## FAQ |
| | ### What does "rc" stand for in ".bashrc"? |
| | It "run commands". All commands in `~/.bashrc` are run whenever the shell starts. |
| |