- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
It is not obvious from the descriptions of the L2 cache sizes using CPUID(4) and CPUID(80000006h) in the software developer's manual volume 2 (325383-063US), why the two inquiry methods would return different sizes.
CPUID(80000006h) returns (eax, ebx, ecx, edx): 0 0 0x1006040 0. Documentation says that bits 31:16 of ecx is L2 cache size in K units, which translates to 256K.
The L2 cache information from CPUID(4) returns (eax, ebx, ecx, edx): 0x7c004143 0x3c0003f 0x3ff 0, which according to (heading page 3-216 Vol 2A.) "INPUT EAX = 04H: Returns Deterministic Cache Parameters for Each Level" size is computed as:
This Cache Size in Bytes
= (Ways + 1) * (Partitions + 1) * (Line_Size + 1) * (Sets + 1)
= (EBX[31:22] + 1) * (EBX[21:12] + 1) * (EBX[11:0] + 1) * (ECX + 1)
Which I believe given the ebx/ecx values comes to 1048576.
/proc/cpuinfo (Linux) shows:
processor : 0
vendor_id : GenuineIntel
cpu family : 6
model : 85
model name : Intel(R) Xeon(R) Gold 6148 CPU @ 2.40GHz
stepping : 4
microcode : 0x200004d
cpu MHz : 1000.000
My question is: which method is correct? The 1MB L2 cache size as returned by CPUID(4) seems to match with all public information for this processor/model.
BTW, the discrepancy in L2 sizes only seems to happen with the Skylake Xeon processor that I have access to.
Dave
Here's my driver to the CPUID calls:
#include <stdio.h>
#include <stdint.h>
int cpuid_ecx(uint32_t eax, uint32_t *res, uint32_t ecx)
{
asm("cpuid"
: "=a"(res[0]), "=b"(res[1]), "=c"(res[2]), "=d"(res[3])
: "a"(eax), "c"(ecx)
:);
}
int
main()
{
uint32_t r[4];
uint32_t ecx = 0;
uint32_t csz;
cpuid_ecx(0x80000006, r, ecx);
printf("%u %#x %#x %#x %#x\n", ecx, r[0], r[1], r[2], r[3]);
printf("0x80000006 L2 size=%u\n", r[2] >> 16);
while (1) {
cpuid_ecx(0x4, r, ecx);
printf("%u %#x %#x %#x %#x\n", ecx, r[0], r[1], r[2], r[3]);
if (r[0] == 0) break;
csz = (r[1] >> 22) + 1;
csz *= ((r[1] >> 12) & 0x3ff) + 1;
csz *= (r[1] & 0x3ff) + 1;
csz *= r[2] + 1;
printf("L%u size = %u\n", (r[0] >> 5) & 0x3, csz);
++ecx;
}
}
Link Copied
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content

- Subscribe to RSS Feed
- Mark Topic as New
- Mark Topic as Read
- Float this Topic for Current User
- Bookmark
- Subscribe
- Printer Friendly Page