UNIX: One OS To Rule Them All
CS 321 2007
Lecture, Dr. Lawlor
There's a pretty good, short, readable history of UNIX at
unix.org. Go read it. It's good.
There's a much longer, more personal story of
UNIX by Dennis Richie. If you have a chance, check it
out.
Finally, there's a good UNIX family tree and tour of UNIX creators'
beards here.
UNIX doesn't actually do anything amazing not done by other
operating
systems at the time. But it was written by some really smart,
motivated programmers who wanted the machine to "just work
right". UNIX was developed in portable C (alongside the B and
then C languages), because the programmers were tired of porting
bigger
operating systems written in assembly. The biggest and most
significant design feature of UNIX is the use of "interchangable
parts"
everywhere in the OS.
Interchangable Parts
Most other operating systems are made of a few, giant
programs.
For example, Microsoft Visual C++, and Mac OS Xcode are both huge
"Integrated Development Environments". They've got editors,
debuggers, compilers, and a build system all wrapped together into
one
piece.
There are advantages to this approach. For example, it's easy
to
flip between editing and debugging code, since there's just one big
program running.
But there are also disadvantages. For example, if you hate the
Visual C++ editor, it's not easy to replace it with another editor.
UNIX development works differently. Entirely separate programs
handle editing (nedit, pico, emacs, vi, ...), debugging (gdb, ddd,
TotalView, ...), compiling (g++, icpc, ...), and building (make,
ant,
jam, ...). If you want to add your own specialized tool to the
list, it's trivially easy, because none of the other tools know
about
each other.
For example, here's how I write code:
- Edit: nedit foo.cpp &
- Compile: g++ foo.cpp -o foo
- Run or Debug: ./foo
or gdb ./foo
There's a nice little classic-UNIX program for automating the build
process called "make". "make" is controlled by a little text
file
called a "Makefile".
Basically the above means there's a program "foo". "foo"
depends
on "foo.cpp", which needs to be compiled using "g++". Here's
what
our Makefile would contain:
foo: foo.cpp
g++ foo.cpp -o foo
Note that there's a TAB in front of all commands in Makefiles, not a set of
spaces! This whitespace dependence is by far the worst thing
about Makefiles. (slightly
longer Makefile tutorial)
List of UNIXes
UNIX-like operating systems today include (the short list):
- Almost every existing OS except Windows.
UNIX-like operating systems today (the not-so-short list):
- Linux. Built by random hackers from scratch. Most
insanely popular UNIX ever created. Started as a course
project
in 1993 by a Finnish CS undergraduate named Linus Torvalds.
- Mac OS X. Built by Apple on BSD/Mach "microkernel", a
sort
of kernel-inside-the-kernel. Evolved from NeXTStep in the
late
1990's.
- Sun Solaris. Built by Sun Microcomputer since the
1980's. Still clinging to life from the Linux onslaught.
- HP-UX. HP's UNIX.
- A/IX. IBM's UNIX. Seems to be dying out, even
inside IBM.
- SGI IRIX. Now-defunct Silicon Graphics Inc operating
system.
The general rule: if it's got an "X" in the name of the OS, it's a
UNIX machine.
I tend to treat all UNIX machines interchangeably.
Occasionally
you'll find some annoying difference between them, but the vast
majority of your code will work perfectly on any of these machines.
UNIX Boot Process
A PC starts running UNIX in the boot block, like any PC operating
system. The boot block loads the OS loader, nowadays often GRUB or the older LILO.
The
OS loader loads the UNIX kernel, which is the code that runs with
the supervisor bit set to kernel mode. The UNIX kernel then
finds
the filesystem, and then starts up the first process, which is
always
called "init" and stored in "/bin/init" or "/etc/init". On
most
machines, init then reads /etc/inittab to figure out how to run the
startup scripts, which eventually drop you into a GUI (often some
flavor of X windows) or a text-based
login screen.
This means you can build a new UNIX system by:
- Making a filesystem (for Linux, usually ext2 or ext2) on your
disk.
- Copying a bootloader, kernel, and "init" program onto the
disk.
- Setting up the boot block to point to the bootloader.
That's it.