Welcome to Pipex! π This is a project from Rank 2 at 42 School that introduces us to the world of pipes, processes, and inter-process communication in Unix systems. The goal is to recreate the behavior of shell pipes using system calls like pipe()
, fork()
, dup2()
, and execve()
.
This project simulates the shell command: < file1 cmd1 | cmd2 > file2
π
pipex/
βββ include/pipex.h # Header file (.h)
βββ src/ # Source files (.c)
β βββ main.c # Main program logic
β βββ processes.c # Process management
β βββ execution.c # Command execution
β βββ errorhandler.c # Error handling
βββ obj/ # Object files directory
βββ libft/ # Libft library
βββ .gitignore
βββ Makefile # Makefile to compile the project
βββ README.md # This file
main(int argc, char **argv, char **envp)
: Entry point, validates arguments and orchestrates the pipelinechild_process(int *pipe, char **argv, char **envp)
: Handles the first command executionparent_process(int *pipe, char **argv, char **envp)
: Handles the second command execution
execute(char **envp, char *argv)
: Executes commands using execve()error(int code)
: Handles different types of errorsfree_split(char **split)
: Frees memory allocated for split arrays
- Argument Validation: Checks for exactly 4 arguments (input file, cmd1, cmd2, output file)
- Pipe Creation: Creates a pipe for inter-process communication
- Process Forking: Creates child and parent processes
- File Redirection: Redirects input/output using
dup2()
- Command Execution: Executes commands using
execve()
- Pipes: Used for communication between processes
- Fork: Creates separate processes for each command
- Dup2: Redirects file descriptors for input/output
- Execve: Replaces process image with command execution
- Wait: Parent process waits for child completion
To compile the program, run:
make
This will generate the pipex
executable.
The program takes exactly 4 arguments:
./pipex file1 cmd1 cmd2 file2
Where:
file1
: Input file to read fromcmd1
: First command to executecmd2
: Second command to executefile2
: Output file to write to
./pipex input.txt "grep hello" "wc -l" output.txt
Equivalent to: < input.txt grep hello | wc -l > output.txt
# Count lines containing "error" in a log file
./pipex server.log "grep error" "wc -l" error_count.txt
# Extract and sort unique usernames
./pipex users.txt "cut -d: -f1" "sort -u" sorted_users.txt
# Find and count .c files
./pipex file_list.txt "grep '\.c$'" "wc -l" c_files_count.txt
- Process Management: Understanding how to create and manage processes with
fork()
- Inter-Process Communication: Learning to use pipes for data transfer between processes
- File Descriptor Manipulation: Mastering
dup2()
for input/output redirection - System Calls: Working with low-level system functions
- Command Execution: Understanding how shells execute commands with
execve()
- Error Handling: Proper error management in system programming
- β Handle exactly 4 arguments
- β Create a pipe between two commands
- β Execute commands in separate processes
- β Handle input/output file redirection
- β Proper error handling for all edge cases
- β No memory leaks
- β Handle command not found errors
- β Behave exactly like shell pipes
pipe()
: Creates a pipe for inter-process communicationfork()
: Creates a new processdup2()
: Duplicates file descriptors for redirectionexecve()
: Executes a commandwait()
: Waits for child process completionopen()
: Opens files for reading/writingclose()
: Closes file descriptors
The program handles various error conditions:
- Invalid arguments: Wrong number of arguments
- File errors: Input file not found, output file creation failed
- Pipe errors: Pipe creation failure
- Fork errors: Process creation failure
- Command errors: Command not found or execution failure
- Permission errors: Insufficient file permissions
While the basic version handles two commands, the implementation can be extended to support multiple commands in a pipeline.
The project can be extended to support here_doc functionality:
./pipex here_doc LIMITER cmd1 cmd2 file
Test your pipex with various commands:
# Test basic functionality
./pipex /etc/passwd "grep root" "wc -l" output.txt
< /etc/passwd grep root | wc -l
# Compare outputs - they should be identical
- Understand the pipe mechanism - Data flows from write end to read end
- Close unnecessary file descriptors - Prevent resource leaks
- Handle edge cases - Empty files, non-existent commands, etc.
- Test with real shell commands - Compare behavior with actual pipes
- Use proper error codes - Different errors should have different codes
Made with β€οΈ at 42 Madrid