What happens where you type ls -l in a Linux Shell?
Before starting we have to be clear about some concepts such as shell, terminal and command line.
Shell, the shell or command interpreter is the computer program that provides a user interface to access the services of the operating system. It is the program that receives the commands from the keyboard and gives the orders to the operating system to execute.
The most widely used shell is one called bash which stands for “Bourne-again shell”, and is used on Linux Systems. In almost all the Linux machines, bash is set as the default shell program and will be located in the /bin directory.
Terminal, in computing, is called a terminal or console (hardware) to an electronic or electromechanical device that is used to interact with a computer. The concept of terminal is often confused with that of virtual emulator, which consists of a program that emulates the specifications of a standard terminal. A terminal, for its part, can be defined as each of the computers connected to the network. Also called a node or workstation
Command line, the command-line interface or command-line interface (CLI) is a method that allows users to give instructions to a computer program through a simple line of text. It should be noted that the concepts of CLI, shell and terminal emulator are not the same since CLI is a method while shell and terminal emulator are computer programs. However, all three are often used synonymously.
(photo example of bash)
To better understand all this and how it works, let's see what happens when in a shell we type ls -l and hit enter.
The immediate result of giving this command is to get the files in the current directory where the command was executed. The list will be obtained in what is called a long list format, we ask for this by passing the -l argument.
In order, the steps that a shell executes, based on the Narita Simple Shell (https://github.com/Ksualboy/simple_shell) that we created and considering that it is already compiled and executed are:
The shell is waiting for the user who must enter the commands. The Shell will read what the user types through the Getline function and save it in a buffer.
$ ls -l
Now that we have obtained the entered data, we must divide them into parts which we will call tokens, these tokens in this case will be divided by a space. So we have two tokens, 1) ls and 2) -l. ls corresponds to the command and -l to the argument or flag. The function used in this case to do the division and save it in individual tokens is Strtok.
We analyze the tokens obtained through Strtok, if we see that they are aliases, builtins (in our Narita Simple Shell we have 2 (env and exit)) or if they are commands and where they can be executed. If the command can be executed directly in the shell in the same directory where we are standing or if we have to go through the entire PATH to find where it can be executed. It can even happen that the order we put cannot be executed and in that case it would give an error (file not found).
For the purpose of PATH, PATH is an environment variable that specifies the directories where the executable commands of the operating system are. In our example for ls it is in /bin/ls.
Finally we execute the program (ls) with its arguments (ls -l). For this we will use 3 systems calls, fork (), execve () and wait ().
A last concept that is basic in each operating system. Each instance of a program is known as a process and each process has a number (ID) that allows us to identify them.
Fork will create a new process called child. The child process is an exact copy of the parent process and will run, like the parent, the same program. We use execve to execute the command (ls -l) in the child process while in the parent we execute wait (). The wait () is the system call that is responsible for making the parent wait while the child executes the order. When the child exits and the process is finished (exit ()), the loop will continue from the parent's process. Basically after the command (ls -l) is executed the child process exits and the parent process continues from the point where the child was created (before execution), waiting at the prompt for more user input.
This cycle will continue forever until the user exit the shell.
And thats it!