🚀 Alguni Start learning

Unit 6: Programs Running

Starting, stopping, and did it work?

Unit 6 of 8 in Linux and the command line for kids. Its 5 lessons are A Program With a Number, In the Background, Stopping Things, Did It Work? and Mission Control — below is everything each one explains, and a question or two from it to try.

Every terminal session on this page was replayed before it shipped, on a machine whose every message is tested against real bash and coreutils.

This unit opens with a fortnight’s trial of everything — no card needed — or with a family plan, bought in the iPhone app. The first two units of every track are free for ever. Try it in the app.

🏷️ A Program With a Number

Running, not just sitting there

A program on the disk is a file. A program that is running is something else, and Linux calls it a process.

Every process gets a number when it starts — its PID, or process id. That number is how you talk about it later.

Terminal

kid@alguni:~$ ps
    PID TTY          TIME CMD
    412 pts/0    00:00:00 bash
    940 pts/0    00:00:00 ps

Reading the list

ps shows what is running. There is always at least one: the shell itself, which is a program like any other.

And ps appears in its own list, because at the moment it looked, it was running too.

Try it yourself

What is a PID?

  • The number Linux gives a running program
  • The size of the program
  • How long it has been running
  • The program's password

Answer it in the app

🌗 In the Background

Waiting for a slow program

Normally the shell starts your command and waits for it to finish. That is fine for ls. It is annoying for something that takes ten minutes.

Put & at the end and the shell starts it and hands you the prompt straight back. The program carries on in the background.

Terminal

kid@alguni:~$ sleep 30 &
[1] 940
kid@alguni:~$ jobs
[1]+  Running                 sleep 30 &

What it tells you

[1] 940 is two numbers, not one.

[1] is the job number, which is the shell counting your background jobs: one, two, three.
940 is the PID, which is Linux counting every process on the whole machine.

jobs lists yours. ps lists everything.

Terminal

kid@alguni:~$ sleep 60 &
[1] 940
kid@alguni:~$ sleep 90 &
[2] 941
kid@alguni:~$ jobs
[1]-  Running                 sleep 60 &
[2]+  Running                 sleep 90 &
kid@alguni:~$ ps
    PID TTY          TIME CMD
    412 pts/0    00:00:00 bash
    940 pts/0    00:00:00 sleep
    941 pts/0    00:00:00 sleep
    942 pts/0    00:00:00 ps

Try it yourself

What does the & on the end of a command do?

  • Runs it in the background and gives you the prompt back
  • Runs it twice
  • Runs it as root
  • Joins it to the next command

Answer it in the app

🛑 Stopping Things

Ctrl and C

If a program is running in front of you and you want it to stop, hold Ctrl and press C.

That is not typing a command — it is a signal, sent straight to whatever is running. It is the single most useful key combination on a Linux machine, and every terminal in the world understands it.

Stopping something in the background

Ctrl-C only reaches the program in front of you. For a background job you have to say which one, and that is what the number is for.

kill 940 uses the PID. kill %1 uses the job number. Both do the same thing.

Terminal

kid@alguni:~$ sleep 60 &
[1] 940
kid@alguni:~$ jobs
[1]+  Running                 sleep 60 &
kid@alguni:~$ kill %1
kid@alguni:~$ jobs

A word that sounds worse than it is

kill sounds dramatic. All it really does is send a message to a process asking it to stop, and most programs tidy up and go quietly.

A process that ignores you can be given the message it cannot refuse — kill -9 — but that is a last resort, because it never gets the chance to save anything.

Try it yourself

A program is running in front of you and will not stop. What do you press?

  • Ctrl and C
  • Escape
  • Ctrl and S
  • Enter, lots of times

Answer it in the app

✅ Did It Work?

Every command leaves a verdict

When a program finishes it hands back one number. Zero means it worked. Anything else means it did not.

You do not normally see it, but the shell keeps it, and $? is how you ask.

Zero for success looks backwards until you notice there is only one way to succeed and lots of ways to fail — so every other number is free to mean *which* failure.

Terminal

kid@alguni:~$ cat there.txt
hi
kid@alguni:~$ echo $?
0
kid@alguni:~$ cat missing.txt
cat: missing.txt: No such file or directory
kid@alguni:~$ echo $?
1

And, and or

You rarely read $? yourself. What you do instead is let the shell read it.

&& — run the next one only if that worked.
|| — run the next one only if that failed.

Read them as "and then" and "or else".

Terminal

kid@alguni:~$ cd project && echo "made it"
made it
kid@alguni:~/project$ cd nowhere && echo "made it"
bash: cd: nowhere: No such file or directory
kid@alguni:~/project$ cd nowhere || echo "could not"
bash: cd: nowhere: No such file or directory
could not

Why it matters

This is the difference between a command that is safe and one that is not.

cd photos && rm * deletes things in photos, and does nothing at all if that folder is missing.

cd photos ; rm * deletes things wherever you happen to be standing when cd fails. The semicolon just means "then", with no checking. One character apart.

Try it yourself

What does the last line print?

Terminal

cat real.txt
echo $?

What does mkdir photos && cd photos do if mkdir fails?

  • Nothing — the `cd` never runs
  • It runs the `cd` anyway
  • It tries the mkdir again
  • It stops the terminal

Answer them in the app

🏆 Mission Control

Everything running at once

You are looking after a machine with jobs on it. You will need all of it: ps to look, & to start, jobs to list, kill to stop, and && to only do the next thing if the last one worked.

Try it yourself

Which of these is safe if the photos folder does not exist?

  • cd photos && rm *.jpg
  • cd photos ; rm *.jpg
  • rm *.jpg ; cd photos
  • cd photos || rm *.jpg

Answer it in the app