Lecture 4 – Sep 13th, 2022
Setup
- Log on to clyde:
ssh user@clyde.cs.oberlin.edu
. - Create a directory with whatever name you like and
cd
into it.
Task
- The command
$ ls /bin /usr/bin
will print out a list of all the files in/bin
and/usr/bin
. Each of these is a program you can run, but there are likely too many to display in your terminal. So run the command again, but redirect the output to a file calledbinaries
. - Run
$ wc -l binaries
to see how many lines are in the file. - Open the file with your favorite command line editor (e.g.,
nvim
,vim
,emacs
,nano
) and take a look at the output. Is the number you printed out in step 2 the actual number of binaries? Hint: Look closely at the first line. - One thing to notice is the output from
ls
is different when directed to a file than it is when it goes to the terminal. It turns out that programs can detect if theirstdout
is connected to a terminal or not. Some programs use this ability to change their output, some do not. Run$ man isatty
and take a look at the manual page for theisatty()
function. This is a C function and we’ll get to programming in C soon enough. For now, it’s enough to know thatstdout
is file descriptor1
so the function callisatty(1)
tells the program ifstdout
is a terminal or not. - Let’s figure out how many binaries start with the letter
z
by usinggrep
. Recallgrep
reads files (orstdin
) and prints lines matching a pattern. Run$ grep z binaries
. Notice that it prints out all lines containing az
. That’s not what we want, but we’re close. - Grep interprets the
^
character to mean “match the beginning of the line” so$ grep ^z binaries
should do what we want. Run that and look at the output. -
Let’s figure out how many of them there are. Rerun that
grep
command and redirectstdout
to a filezfiles
. Run the appropriatewc
command to figure out how many there are.To recap what we’ve done so far, we created a file containing a list of all of the binaries in
/bin
and/usr/bin
. We usedgrep
to extract just those that start withz
and stored that in a file. Finally, we ranwc
on that to figure out how many there are. Pretty simple but we had to create two files for it that we don’t really care about if our goal was just to figure out that final number. -
We can skip the creation of the first file by piping the output of
ls
togrep
and storing the result to a file. Explicitly,$ ls /bin /usr/bin | grep '^z' >zfiles1
Notice that we don’t specific a file name for
grep
. When we omit it, it reads fromstdin
. -
Let’s check that the two files we just created are identical by using the
diff
program to print out the differences between two files. Run$ diff -u zfiles zfiles1
Nothing should be printed when you do that because the files should be the same.
- Append a line of text (anything you want) to
zfiles1
usingecho
with an append redirection (>>
). - Rerun the
diff
command from step 9. You should see some output. (Diffing files is extremely useful. We’ll see more of this later and you’ll see a lot of it as you program more.) - Enough
diff
for now. In step 8, we skipped the creation of one file by using a pipe but we still created a second file. Construct a new command piping the output ofls
togrep
and piping that output towc
. You should get exactly the output you got in step 7. - We actually did more work than we needed to. Remember that the shell will
expand wildcards that match file names. For example,
/bin/z*
will be expanded to the paths of all of the files that match that pattern. Run$ echo /bin/z*
to see the result. -
Using
ls
rather thanecho
(becauseecho
prints a single line and we want multiple lines) and the appropriate patterns, construct a pipeline to count all of the binaries starting withz
again. That is, fill in the missing bits in$ ls [...] | wc -l
- That’s enough for today. You can delete the directory you created.