Hi,
a5498828 wrote:1. how does PCD/PWT work?
for example, PDE has PWT = 1, PTE has PWT = 0, will that page be write-through?
All of the cache controls can only be used to reduce caching. This means that if the CR0 (and CR3) and the MTRRs all say "write back", but the PDE has PWT=1 ("write-through") then you get "write-through" (because it's more restrictive); and the PTE can't be used to increase the caching to "write-back" again (but could be used to reduce caching more by using PCD=1 to make it "uncached").
a5498828 wrote:2. i dont quite understand pat thing.
Originally there was no PAT, and page directory/table entries had the PCD/PWT flags and nothing else. This let you choose "write-back", "write-through" or "uncacheable". Then Intel added a new caching type ("write combining") and wanted to use the page directory/table entries to let you choose "write combining" and "write protected" too. That gives 5 different caching types, which is too much for 2 bits. They had to use a third bit (and they did).
However, for backward compatibility they couldn't guarantee that older software didn't set the new third bit. To get around that they used the 3 bits as an index into a lookup table (for e.g. "
PAT_index = PWT_flag | (PCT_flag << 1) | (PAT_flag << 2);" and then "
cache_type = PAT[PAT_index];"), where (by default) the last 4 entries in the lookup table are the same as the first 4 entries in the lookup table. This means that, for older software, it didn't make any difference if the third bit was set or not - the software still got the same caching type it originally expected. New software that is designed to use PAT can change the table (which is stored in a 64-bit MSR, with 8-bits per entry and 8 entries), which gives new software a way to use all 3 bits to select any of the 5 caching types.
a5498828 wrote:3. how does mtrr work? i have intel and amd manuals, and i cant find anything about it.
It is in the Intel's "System Programming Guide" and AMD's "System Programming" manual (and so is information for the PAT).
For MTRRs, the basic idea is to use the physical address to find the caching type. There's 2 types of MTRRs - the "fixed range MTRRs" (which are used for the first 1 MiB of the physical address space, and work like a lookup table). There's also "variable range MTRRs" which are more flexible and can be used to set the cache type for arbitrary areas of the physical address space (but there's a limited number of variable range MTRRs - typically only about 4 of them). Lastly there's a default caching type, which is used if the physical address is above 1 MiB (not in the fixed range MTRRs) and not described by any variable range MTRRs.
Usually, an OS can expect the firmware (e.g. BIOS) to setup the MTRRs properly, except that the firmware won't setup an area suitable for the video card/s' display memory (or other devices that use memory mapped I/O). The firmware is also expected to leave at least one variable range MTRR free, so that an OS can use it to setup an area suitable for at least one video card's display memory. You shouldn't need to touch the existing MTRRs that were setup by the firmware; but for a variety of reasons (e.g. to make sure that the maximum number of variable range MTRR are free) some OSs (e.g. Linux) can/do completely reprogram the MTRRs (even though it shouldn't be necessary).
Cheers,
Brendan