Hack/Jack analogs in "real" platforms and the VM abstraction
I finished the TECS projects several weeks ago but still think about them on a daily basis, as they provided the foundation of my current meager understanding of hardware, software, and all the layers of abstractions involved in the interface. I don't know too much about "real world" hardware and software platforms, but I understand they operate in a similar fashion. However, the one abstraction from TECS that was the hardest for me to relate to what I understand of real computers was the VM stage. For one, in my mind the VM concept is already associated with something much more complex, i.e. running a virtual computer inside a computer (like with VMware or something). But I guess a stack-based machine abstraction is the most minimal version of that, sort of like the Jack "operating system" consisting of little more than I/O and Math libaries is a very minimal version of what I'm used to calling an operating system in the real world (Windows). Or maybe that is a different kind of VM, designed for a different purpose than the stack-based machine abstraction presented in TECS.
My main question though: in a real high level language like C, is there a VM abstraction between C code and assembly code for whatever hardware it's being compiled for? I've heard of "object code" before but I don't know very much about it.
I know with Java obviously there is the JVM, but that is more for portability than it is just for the sake of a conceptual abstraction to make coding easier (I kind of felt like the latter was the purpose of the VM in TECS... is that right?). Plus when I think of a high level language in which one writes OS's, I think of C. Based on how I've used PC's in the real world, the VM is a program which gets installed on top of an OS, versus here how we wrote an OS on top of a VM.
VM is an multiply defined term. The type of Virtual Machine that you are talking about—JVM, Windows 7's and Linux's VMs that let them host each other OS, etc.—are system applications that run on top of the native OS.
The VM in TECS might better be called a Virtual Machine Architecture since it is only an abstraction that is used as an interface between the front and back ends of the Jack compiler. The "VM" you wrote is really a code generator for your Jack compiler.
There are many compilers in the real world that are written this way. Many (most?) of the C compilers I use are derived from GNU C with code generators written specifically for the targeted microprocessor. Only minor changes are required to the front end, usually to support odd memory architectures.
Consider a slightly more sophisticated Hack computer that allowed a program to read data from ROM. A Hack VM program could be stored in ROM and a program could be written that interpreted the VM program line by line and did the required operations. This program would be a VM in the more general sense.