支持多种页面大小的 TLB 有许多可能的设计,并且权衡很重要。但是,我将仅简要讨论商业处理器中使用的那些设计(请参阅this 和this 了解更多信息)。
一个直接的问题是如何在访问集合关联 TLB 之前知道页面大小。要映射到物理地址的给定虚拟地址必须按如下方式进行分区:
-----------------------------------------
| page number | page offset |
-----------------------------------------
| tag | index | page offset |
-----------------------------------------
索引用于确定要查找的TLB集合,标签用于确定该集合中是否有匹配的条目。但是只给定一个虚拟地址,不访问页表项就无法知道页大小。如果不知道页面大小,则无法确定页面偏移的大小。这意味着构成索引和标签的位的位置是未知的。
大多数商业处理器使用两种设计之一(或两者)来处理此问题。第一种是使用并行 TLB 结构,其中每个 TLB 仅指定用于特定大小的页面条目(这并不精确,见下文)。并行查找所有 TLB。可以是单次命中,也可以是全部未命中。也有可能发生多次命中的情况。在这种情况下,处理器可能会选择其中一个缓存条目。
第二种是使用全关联TLB,其设计如下。令 POmin 表示体系结构支持的最小页面大小的页面偏移大小。让 VA 表示虚拟地址的大小。在全关联缓存中,地址被划分为页偏移量和标签;没有索引。令 Tmin 表示 VA - POmin。 TLB 被设计成每个条目都保存一个大小为 Tmin 的标签,而与缓存在该 TLB 条目中的页表条目的页面大小无关。
虚拟地址的 Tmin 最高有效位在全关联 TLB 的每个条目处提供给比较器以比较标签(如果条目有效)。比较如下进行。
| M |
|11|0000| | the mask of the cached entry
-----------------------------------------
| T(x) |M(x)| | some bits of the offset needs to be masked out
-----------------------------------------
| T(x) | PO(x) | partitioning according to actual page size
-----------------------------------------
| T(min) | PO(min) | partitioning before tag comparison
-----------------------------------------
TLB 中的每个条目都包含一个称为标签掩码 的字段。令 Tmax 表示该架构支持的最大页面大小的标签大小。那么标签掩码的大小 M 为 Tmin - Tmax。当页表条目被缓存在 TLB 中时,掩码的设置方式使得当它与给定标记(Tmin)的相应最低有效位进行按位与运算时,属于页面偏移字段的任何剩余位都将变为全零。此外,存储在条目中的标记附加了足够数量的零,使其大小为 Tmin。所以掩码的一些位会是 0,而其他位会是 1,如上图所示。
现在我将讨论几个示例。为简单起见,我假设没有超线程(可能的设计选项包括共享、静态分区和动态分区)。 Intel Skylake 为 L1 D/I TLB 和 L2 TLB 使用并行 TLB 设计。在Intel Haswell 中,L2 TLB 不支持 1 GB 页面。请注意,4 MB 页面使用两个 TLB 整体(带有复制标签)。 我认为 4 MB 页表条目只能缓存在 2 MB 页条目 TLB 中。 AMD 10h and 12h 处理器使用完全关联的 L1 DTLB、并行的 L2 DTLB、完全关联的并行 L1 ITLB 和仅支持 4 KB 页面的 L2 ITLB。 Sparc T4 处理器使用完全关联的 L1 ITLB 和完全关联的 L1 DTLB。 Sparc T4中没有L2 TLB。