Minishell is a simplified but fully functional recreation of the Bash shell. This project involves deep interaction with the Linux Kernel API, managing processes, memory, and file descriptors manually.
It is not just a command runner; it is a full interpreter that parses user input, handles variable expansion, manages a command history, and controls execution flow using pipes and redirections.
| Category | Features Implemented |
|---|---|
| Parsing | Handles single quotes ', double quotes ", and environment variable expansion ($USER, $?). |
| Redirections | Input < output >, append >>, and Here-Doc << support. |
| Pipes | Connects multiple commands (`cmd1 |
| Signals | Custom handlers for Ctrl-C, Ctrl-D, and Ctrl-\ using sigaction. |
| Execution | Uses execve, fork, waitpid to manage child processes without zombies. |
| History | Persistent command history (up arrow navigation). |
My shell implements the following built-ins from scratch, mirroring Bash behavior:
echowith option-ncdwith relative or absolute pathspwdto print working directoryexportto manage environment variablesunsetto remove environment variablesenvto print current environmentexitto terminate the shell cleanly
The shell operates in a continuous Read-Eval-Print Loop (REPL):
- Lexer/Tokenizer: Splits the raw input string into tokens (Words, Operators, Pipes).
- Parser: Organizes tokens into a structured command table (AST or Linked List).
- Expander: Replaces
$VARwith values from the environment array. - Executor:
- Creates pipes if needed.
fork()processes.- Redirects Standard I/O using
dup2(). - Executes binary using
execve().
// Simplified Execution Logic
if (fork() == 0) {
dup2(fd[1], STDOUT_FILENO); // Connect Pipe
close(fd[0]);
execve(cmd, args, env); // Replace process
} else {
waitpid(-1, &status, 0); // Parent waits
}π Installation & Usage Prerequisites GCC Compiler
GNU Readline Library
Building
git clone https://github.com/70rn4d0/MiniShell.git
cd MiniShell_tty
makeRunning
./minishellExample Usage
minishell$ ls -l | grep ".c" | wc -l
minishell$ export 1337="Best School"
minishell$ echo $1337
Best School