PC keyboards
You will notice that modern PC keyboards have those little "windows" and "application" keys between the Ctrl and Alt keys either side of the spacebar. That is a Microsoft protocol: you've got a
Windows Keyboard. Yep, a keyboard designed for your OS.
http://en.wikipedia.org/wiki/Windows_key
Keyboard layout and shortcuts
http://www.internet4classrooms.com/winkeyboard.htm
http://www.seoconsultants.com/windows/keyboard/
PC keyboards work by signalling a hardware interrupt. The OS then reads (port $60 I think) to obtain the code in the keyboard's memory buffer. This is usually a "make" or "break" code: "make" for key presses (bit 7 clear), and "break" for key releases (bit 7 set). Each code is therefore seven bits wide --enough for 128 different keys.
When getch() and the like were first designed, the question was: what exactly is the ASCII char for <left arrow>? BASIC did it by co-opting the US,FS,RS,GS ASCII codes, but the DOS services decided against changing the meaning of specific ASCII codes and simply returned
two values: a zero to signify that what follows was not an ASCII code, and then the actual keyboard scancode (sans the make/break bit). The numeric keypad, for example, has for keys '1'..'9' the scancodes 71,72,73,75,76,77,79,80,81.
The original XT keyboards worked exactly as you would expect: each key had its own number. With the advent of the 101/102-key AT keyboards, we started to see some "escape" codes --values that signalled that the next code is for some special key but were otherwise meaningless by themselves. The special code was... <drumrolll> ... E0h. The purpose was obstensively that the OS was to intercept the next key instead of the active application program.
Today there are a lot of keys or key combinations that have extended key sequences (two or three key codes). If you are up to a good read then check out this page all about PC scancodes:
http://www.win.tue.nl/~aeb/linux/kbd/scancodes.html
Other keyboards
One of the things that made the PC so popular was the hardware specification standardization. Not so in the mainframe and mini world. It seemed at times that various keyboard manufacturers tried to out-do themselves with new and different keyboard designes. Some keyboards can send as many as (I think) fifteen codes for a single key press (though granted, that would be for some oddball, non-alphanumeric key).
Between the CRT and keyboard, the difficulty of dealing with all the weird and wacky hardware combinations caused the birth of the
termcap database: a huge text file that lists hardware by its name (or name
s!) and all the codes needed to communicate with it.
It was a bit of a mess, so one day
esr decided to clean it up a bit and now we have the
terminfo database and (n)
curses libraries to make playing with the hardware easy. (Well, easier than it was, at least. RU, for example, refuses to update its local terminfo databases to match the actual hardware in use because the suits want the OS to "meet the specs" across all campuses. Which sort of defeats the purpose of having the database to begin with... but enough about that.) Some hardware is so weird and/or undocumented and/or ancient that the terminfo database lacks more than the most basic data for it.
X makes things a lot easier because it handles all the hardware oddities for you and provides a nice, simple interface for your application programs. You don't even have to do anything but tell X what key events you want to know about, and it will deliver keystrokes to your application's doorstep, as it were, all nice and packaged and pretty. (Windows does the same thing, BTW. You could technically run Windows using a SunSPARC keyboard.)
getch()
The getch() function was invented by Microsoft (
not Borland, as I also used to think) as a convenient interface to the DOS 21h services (function 07h I think, direct console input, no echo). Borland expanded upon it and just skipped the OS and went directly to the hardware (which in those days, actually had an observable difference in speed). As such, the getch() function has always been fairly tied to the Intel PC hardware, and not very translatable to other systems (it can be done, but it is invariably not worth the grief).
[edit]
^] means Ctrl ']', which is the Escape key code.