
- •3.1 Structure
- •3.1.1 Layers of Software
- •Layers and Process Management
- •Encapsulation and Abstraction
- •Layers of Software
- •3.1.2 The bios: Life at the Bottom
- •The Role of the bios
- •Changing bios Settings
- •3.1.3 Process Control
- •3.2 Device Management and Configuration
- •3.2.1 Interrupt Handling
- •Interrupts
- •Interrupt Priority and Nested Interrupts
- •Traps and Faults
- •3.2.2 Hardware Attributes
- •Installing Drivers
- •Changing a Driver's Configuration
- •3.2.3 Configuration
- •3.3 Resource Sharing
- •3.3.1 Virtual Memory
- •Managing Memory
- •Relocation
- •Virtual Memory
- •3.3.2 File and Printer Sharing
- •Printers
- •3.4 File Systems
- •3.4.1 File Organization
- •Folders
- •Shortcuts
- •File Names and Types
- •3.4.2 File Allocation Table and nt File System
- •Clusters and File Allocation Tables
- •Nt File System
Virtual Memory
In a virtual memory system, every program runs in its own private address space. Thus, there is no need for any relocation when the program is loaded into memory. A virtual address space can be larger or smaller than the processor's physical memory. In order for this scheme to work, though, virtual memory requires hardware support. First, memory is divided into chunks called pages. A page is the smallest piece of memory that can be allocated to a program. On Pentium platforms, a page is 4 KB. Second, the processor must have a way of turning virtual addresses into real ones.
Processors that support virtual memory, such as the Pentium, can run in two modes. In real mode, addresses refer to physical locations in RAM. Only the kernel is allowed to run in real mode. In virtual mode, every address is "translated" into a physical memory location by means of a page table. For each page in the virtual address space, the page table gives the real address in RAM where the page is located.
Let us see how this applies to the hypothetical program described earlier. This program will run in its own virtual address space, starting at location zero. When the processor loads the program into RAM starting at location 30,000, it sets the page table entry for page 0 to the value 30,000. Now, when an instruction loads the address at virtual location 210, the processor's address translation circuitry actually causes the data to be loaded from physical location 30,210. The value read from that location in memory will be 30,700 (remember, location 210 holds the address of the table, which is 700), the virtual address of the table. If another instruction then tries to access the table by using this 700 address, once again the address translation mechanism will intervene and convert the reference to location 30,700. The user program only deals with virtual addresses; it has no idea in what portion of physical memory it is running. When the processor is in virtual mode, address translation is happening all the time. Every single memory reference is translated. It happens very quickly because translation takes place on board the processor chip.
With a virtual memory scheme, every program has its own page table, maintained by the kernel. And, physical memory allocated to a program need not be contiguous. Our hypothetical program's page table could say, "Okay, page zero begins at real address 30,000; page one begins at 34,000; page two begins at 62,000; and so on." The user program has no idea that it is spread out across physical memory, because it is living in a virtual world and cannot see the real addresses.
With a little extra help from the hardware, we can carry this scheme one step further and completely divorce virtual memory from RAM. Let us say we do not want to load the entire program into RAM at once, so we only load a couple of pages. For those pages we choose not to load, we put a special marker in the page table that says, "This page is not in RAM." Now the user program starts running, and it makes a memory reference to page zero that is translated nicely. It makes a memory reference to page one, and the processor again looks at the page table and finds the corresponding physical address. Then, the program refers to a memory location that falls on page seven, which we did not load into RAM. The address translation circuitry checks the page table, finds the "not in RAM" marker, and generates a page fault. This is a kind of interrupt. The processor stops executing the user program and gives control to the kernel. The kernel looks at certain status registers to figure out where the page fault came from and says, "Oh, this process wants access to its virtual page seven. I will get some RAM here and load in page seven of the program. Now I will fix update the page table, and I will let the program the instruction again." So, control is returned to the user program, and the program continues as if nothing unusual had happened.
With hardware paging support, user programs really do live in a virtual world. Not only do they not know which chunks of RAM they are using, they do not even know which of their pages are in RAM right now and which are sitting on disk! Every time the process tries to reference a page that is on disk, the page is moved to RAM. And, if the process has not touched a page in a while, it might be moved back to disk. By introducing virtual memory, we have provided user programs with a very clean memory abstraction. They need not worry about sharing the address space with the operating system or with other applications. They need not worry about how much physical memory is on the machine. They have an entire virtual address space to use as they like, and the kernel takes care of the implementation details.
One drawback of using the hard drive for virtual memory is that this can keep the hard drive so busy that access to other files is delayed. For systems that involve frequent file accesses but also require virtual memory, it may be advisable to put the swap file (the file containing all virtual memory pages) on a separate drive.