Red Hat Certified System Administrator (RHCSA) #2 Essential Tools: bash, vi, redirection, find/grep, archive, ssh
If #1 The Exam Introduction gave you a grip on the EX200’s format and testing environment, now we move into the shell fundamentals that everything else is built on. RHCSA is a hands-on exam where you finish tasks in front of an empty shell within a time limit, and what decides your speed is exactly the tools covered in this post. User management, LVM expansion, SELinux fixes — in the end they all come down to typing commands in the shell and checking the result, so redirection, find, grep, and vi need to be second nature before the rest goes fast.
In particular, there’s no internet in the exam room. You can’t reach Stack Overflow or any blog, so if you can’t recall a single find option, your only recourse is to dig through the man page fast. This post is about getting the everyday tools into your hands while also building the habit of finding answers in the man page when you’re stuck.
Input/output redirection and pipes #
Every command in the shell has three channels: standard input (stdin, 0), standard output (stdout, 1), and standard error (stderr, 2). Redirection is the feature that routes these channels to a file or another command, and in RHCSA you use it constantly to save command output to a file or to filter out only the errors.
# standard output to a file (overwrite)
ls -l /etc > /tmp/etc-list.txt
# append standard output to a file (append)
date >> /tmp/etc-list.txt
# only standard error to a file (channel 2)
find / -name "*.conf" 2> /tmp/errors.txt
# standard output and standard error together into one file
find / -name "*.conf" &> /tmp/all.txt
find / -name "*.conf" > /tmp/all.txt 2>&1
# discard errors (ignore warnings from directories without permission)
find / -name "passwd" 2> /dev/null> overwrites the existing content and >> appends to the end. Confuse the two and you can wipe out an entire working file, so when you need to accumulate, always use >>. Sending standard error to /dev/null clears the warnings from directories without permission off your screen.
A pipe (|) passes one command’s output to the next command’s input. Chaining several tools to finish a task in a single line is the heart of the shell.
# count only users whose login shell is bash
grep "/bin/bash$" /etc/passwd | wc -l
# top 5 processes by memory usage
ps aux | sort -k4 -rn | head -5tee saves output to a file while showing it on screen at the same time. It’s handy when you want to check a command’s result and keep a record of it.
# show on screen while also saving to a file
ls -l /var/log | tee /tmp/log-list.txt
# write to a file that needs sudo (redirection is the shell's privilege, so sudo doesn't take)
echo "net.ipv4.ip_forward = 1" | sudo tee /etc/sysctl.d/99-fwd.confThe last example is where people often get stuck in RHCSA. A sudo echo ... > /etc/... form fails with a permission error because the redirection itself is handled by the ordinary-privilege shell. Using sudo tee here makes the file-writing step run as root, which solves it.
find: finding files that match conditions #
A typical RHCSA task is “find the files that satisfy a certain condition and copy them somewhere or change their permissions.” find is the central tool for this work, so get its options into your hands.
# find by name (case-sensitive / case-insensitive)
find /etc -name "*.conf"
find /etc -iname "*.CONF"
# find by type (f=file, d=directory, l=symbolic link)
find /var -type d -name "log"
# find by size (+10M=over 10MB, -1k=under 1KB)
find /var -type f -size +10M
# find by modification time (-mtime -7=within the last 7 days, +30=before 30 days ago)
find /home -type f -mtime -7
# find by permission (exact match)
find / -type f -perm 4000 2> /dev/null
# find by owner / group
find /home -user alice
find /home -group developersThe unit for -size is c (bytes), k, M, G, and prefixing + means over, - means under, and no sign means exactly that size. The number for -mtime works the same way: -n means within the last n days and +n means before n days ago.
Permission searches come up especially often in RHCSA. A task asking you to find SUID files requires -perm -4000, not -perm 4000, to be precise, because prefixing - catches every file that “includes that bit.”
# all files with the SUID bit set (inclusive search)
find / -type f -perm -4000 2> /dev/null
# files that group and others can write to
find /var -type f -perm -022-exec, which applies an action directly to the files you find, is the most powerful. {} is replaced by each file found, and \; terminates the command.
# copy all the .conf files found to /tmp/backup
find /etc -name "*.conf" -exec cp {} /tmp/backup/ \;
# change permissions in bulk on files owned by a specific user
find /shared -user bob -exec chmod 640 {} \;
# delete with a confirmation prompt before running (-ok)
find /tmp -name "*.tmp" -ok rm {} \;A task like “find all files owned by alice and copy them to /root/alice-files” can be done in a single line: find /home -user alice -exec cp {} /root/alice-files/ \;. Get this pattern into your hands and you’ll solve similar tasks fast.
grep: finding within text #
grep picks out the lines that match a pattern from a file or output. It’s the starting point for nearly all the work of digging through logs and checking config files.
# basic search
grep "root" /etc/passwd
# ignore case (-i)
grep -i "error" /var/log/messages
# search a whole directory recursively (-r)
grep -r "PermitRootLogin" /etc/ssh/
# only non-matching lines (-v). often used to strip comments and blank lines
grep -v "^#" /etc/ssh/sshd_config | grep -v "^$"
# show line numbers (-n)
grep -n "listen" /etc/httpd/conf/httpd.confTo see the surrounding context of a matched line, use -A (after), -B (before), and -C (context). It’s handy for examining what came before and after an error in a log.
# the matched line and the 3 lines after it
grep -A 3 "Failed password" /var/log/secure
# the matched line and the 2 lines before it
grep -B 2 "error" /var/log/messages
# the matched line and 5 lines on each side
grep -C 5 "denied" /var/log/audit/audit.logTurn on extended regular expressions with -E. Knowing just the basics of regex makes searches much more precise. ^ is the start of a line, $ is the end of a line, . is any single character, * is zero or more repetitions of the preceding character, and [abc] is a character set.
# lines ending in bash (end-of-line anchor)
grep "bash$" /etc/passwd
# blank lines (nothing between start and end)
grep -c "^$" /etc/ssh/sshd_config
# extended regex: error or warn
grep -E "error|warn" /var/log/messages
# lines with one or more consecutive digits
grep -E "[0-9]+" /etc/hostsText processing tools #
Tools for viewing and trimming file content also show up throughout exam tasks. less pages through a long file one screen at a time, lets you search inside with /pattern, and exits with q. The man page display is also less, so the controls are the same.
# view a file one page at a time (/pattern to search, n for next, q to quit)
less /var/log/messages
# view only the front / back portion
head -20 /etc/passwd
tail -20 /var/log/messages
# follow a log in real time (-f)
tail -f /var/log/messagessort is for sorting, wc for counting lines/words/bytes, and cut for slicing out columns.
# alphabetical / numeric / reverse sort
sort /etc/passwd
sort -t: -k3 -n /etc/passwd # : delimiter, 3rd field as a number
# count lines / words
wc -l /etc/passwd
grep -c "" /etc/passwd
# extract only field 1 (username), delimited by :
cut -d: -f1 /etc/passwd
# cut by fixed width (characters 1〜8)
cut -c1-8 /etc/passwdsed and awk are powerful for one-line transformations. In RHCSA, editing directly with vi is often safer, but for bulk substitution or extracting a specific field, a one-line command is faster.
# sed: substitute oldname with newname on every line (output only)
sed 's/oldname/newname/g' /tmp/file.txt
# sed: modify the file in place (-i), backing up the original as .bak
sed -i.bak 's/PermitRootLogin yes/PermitRootLogin no/' /etc/ssh/sshd_config
# awk: print only the 3rd column, space-delimited
awk '{print $3}' /tmp/data.txt
# awk: : delimiter, print usernames whose UID is 1000 or higher
awk -F: '$3 >= 1000 {print $1}' /etc/passwdvi/vim: the editor you must have for the exam #
In RHCSA, tasks that edit config files directly come up endlessly, and that editing is almost always done with vi. There’s no guarantee nano is always installed, so you must get vi’s basic operations into your hands.
vi is a mode-based editor. Understanding how to switch between the three modes is the starting point.
| Mode | Role | Entry |
|---|---|---|
| Normal | move,delete,copy,paste | Esc |
| Insert | enter text | i, a, o |
| Command-line | save,quit,search-and-replace | : |
The flow of starting an edit, saving, and getting out is as follows.
vi /etc/ssh/sshd_config # open the file (starts in normal mode)
i # enter insert mode (type from the cursor position)
... edit content ...
Esc # back to normal mode
:w # save
:q # quit
:wq or ZZ # save and quit
:q! # force-quit without savingMemorize the common normal-mode operations too. dd deletes a line, yy copies a line, p pastes, u undoes, gg goes to the top of the file, G to the bottom, and <number>G jumps to that line.
Search-and-replace saves you a great deal of time on the exam. In normal mode, search with /pattern and move to the next match with n. The command-line mode substitution uses the following form.
:%s/old/new/g # replace every old with new across the whole file
:%s/old/new/gc # ask for confirmation on each substitution
:10,20s/old/new/ # substitute only on lines 10〜20
:set number # show line numbersA task like “change PermitRootLogin to no in sshd_config” can be solved by opening it in vi, finding it with /PermitRootLogin and editing directly, or changing it all at once with :%s/PermitRootLogin yes/PermitRootLogin no/.
archive: tar, gzip, bzip2 #
Bundling and compressing files is also part of the exam scope. tar bundles several files into one and, depending on the options, handles compression as well. Once you know what the option letters mean, combining them is easy. c is create, x is extract, t is list, f specifies the filename, v shows progress, z is gzip, j is bzip2, and J is xz compression.
# bundle a directory into a gzip-compressed archive
tar czf /tmp/etc-backup.tar.gz /etc
# bundle with bzip2 compression
tar cjf /tmp/etc-backup.tar.bz2 /etc
# extract an archive (gzip)
tar xzf /tmp/etc-backup.tar.gz -C /tmp/restore/
# list contents only, without extracting
tar tzf /tmp/etc-backup.tar.gzDrop the compression letter and bundle with tar cf for a plain, uncompressed archive. As a rule you match the same compression letter when extracting, but recent tar auto-detects the compression format, so tar xf alone usually works. To compress a single file, you can also use gzip and bzip2 directly.
# compress / decompress a single file (replaces the original with .gz)
gzip /tmp/big.log # → big.log.gz
gunzip /tmp/big.log.gz # → big.log
# bzip2 (higher compression, slower)
bzip2 /tmp/big.log
bunzip2 /tmp/big.log.bz2ssh and scp: remote work #
The RHCSA exam sometimes involves multiple systems, so connecting to another host over ssh to work is common. Basic connection and command execution look like this.
# connect to another host
ssh user@server1
# run a remote command without connecting and get the result back
ssh user@server1 'hostname; uptime'
# connect specifying a port
ssh -p 2222 user@server1To connect without a password, set up key-based authentication. Create a key pair and send the public key to the target server. The detailed firewalld and SSH key setup is covered in depth in #12, but get a grip on the basic flow here.
# generate a key pair (private key ~/.ssh/id_ed25519, public key .pub)
ssh-keygen -t ed25519
# copy the public key to the target server's authorized_keys
ssh-copy-id user@server1
# from then on, connect without a password
ssh user@server1File transfer is done with scp and rsync. scp is a simple copy, while rsync transfers only the changes, making it efficient for large directories.
# local → remote
scp /tmp/report.txt user@server1:/home/user/
# remote → local
scp user@server1:/etc/hosts /tmp/
# an entire directory (-r)
scp -r /tmp/configs user@server1:/tmp/
# rsync: only the changes, archive mode to preserve permissions (-a)
rsync -av /tmp/configs/ user@server1:/tmp/configs/Using man pages: the weapon in an exam room with no internet #
There’s no internet in the exam room. When you can’t remember a command option, the man page is your only reference, so the habit of finding it fast is itself points. To find related man pages by keyword, use man -k (apropos).
# find related commands by keyword
man -k password
man -k "list directory"
# open man and find examples inside with /EXAMPLE (less controls)
man find # after opening, type /EXAMPLE, n for nextWhen the same name exists in several sections, specify the section number. Section 1 is user commands, 5 is file formats and config files, and 8 is administrator commands. For instance, passwd exists as both a command (section 1) and a file format (section 5).
# the passwd command (section 1)
man 1 passwd
# the /etc/passwd file format (section 5)
man 5 passwd
# the directory where config example files are gathered (a big help on the exam)
ls /usr/share/doc/Under /usr/share/doc are config examples per package. For tasks with finicky config formats like autofs or LVM, copying an example file and editing it can save a lot of time.
Exam regular: find files matching conditions and process them #
The representative task where this post’s tools all come together at once is “find the files matching a certain condition and copy or bundle them somewhere.” Get a few patterns into your hands and you won’t get stuck even when a similar task appears.
# find all files owned by bob and copy them to /root/bob-files
mkdir -p /root/bob-files
find / -user bob -type f -exec cp {} /root/bob-files/ \; 2> /dev/null
# bundle only the files ending in .conf under /etc into a compressed archive
find /etc -name "*.conf" -exec tar rf /tmp/confs.tar {} \;
# save a list of files under /var/log modified within the last 7 days
find /var/log -type f -mtime -7 > /tmp/recent-logs.txt
# pull only the lines containing error from the messages log into a file
grep -i "error" /var/log/messages > /tmp/errors.txtHere too, always check persistence and accuracy. The small habit of confirming that you created the destination directory first, and that the output is clean with 2> /dev/null filtering out permission-denied warnings, is what keeps you from losing points.
Exam points #
- Distinguishing redirection.
>overwrites,>>appends,2>is errors only,&>is output and errors together. When writing to a file protected by sudo, usesudo tee - Combining find conditions. Combine
-name,-type,-size,-mtime,-perm,-user, and process right away with-exec ... {} \;. For SUID search,-perm -4000 - grep’s regex and context.
-i,-r,-v,-Eand-A/-B/-C. Strip comments withgrep -v "^#" - Essential vi operations. Mode switching,
:wq,:q!,:%s/old/new/gsubstitution. nano may not be there, so learn vi - Combining tar options. Bundle with
czf, extract withxzf, list withtzf - ssh and scp. Distribute keys with
ssh-copy-idto connect without a password, and transfer withscp -r,rsync -av - man pages. Find keywords with
man -k, distinguish identical names by section number, and make use of the examples in/usr/share/doc
Wrap-up #
What this post locked in:
- Redirection and pipes. Route output and errors to a file, chain tools with
|, and save while showing at the same time withtee - find and grep. Find files matching conditions and process them with
-exec, pick out patterns from text and see the context too - Text processing and vi. Handle content with
less,sort,cut,sed,awk, and edit config files directly with vi’s modes and search-and-replace - Archiving and remote work. Bundle with tar,gzip, and exchange files with other hosts using ssh keys and scp,rsync
- man pages. The only reference for finding options in an exam room with no internet
These tools are an exam domain in themselves, and at the same time the foundation that lets you do the work of every other domain fast. I recommend typing them yourself in the environment of the RHEL practical track until they’re second nature.
Next — Shell scripting #
Once the tools are in your hands, you move on to the stage of bundling those tools and automating them.
In #3 Shell scripting: conditionals, loops, arguments, exit codes, we’ll write, hands-on, the basic structure of a bash script, control statements like if,for,while, positional arguments and exit codes, and the simple automation scripts RHCSA requires.