On Tue, Jan 08, 2008 at 04:22:52PM +0100, Alexander Graf wrote: > Mac OS X as is has a condition to only run on family 13 Intel CPUs, so > this adds a definition for a CoreDuo CPU. > Furthermore it adds the MSR Mac OS X uses to read the CPU multiplier and > the CPUID used to read the cache information.
> Index: qemu-snapshot-2008-01-08_05/target-i386/cpu.h > =================================================================== > --- qemu-snapshot-2008-01-08_05.orig/target-i386/cpu.h > +++ qemu-snapshot-2008-01-08_05/target-i386/cpu.h > @@ -232,6 +232,8 @@ > #define MSR_MCG_STATUS 0x17a > #define MSR_MCG_CTL 0x17b > > +#define MSR_IA32_PERF_STS 0x198 > + > #define MSR_PAT 0x277 > > #define MSR_EFER 0xc0000080 > Index: qemu-snapshot-2008-01-08_05/target-i386/helper.c > =================================================================== > --- qemu-snapshot-2008-01-08_05.orig/target-i386/helper.c > +++ qemu-snapshot-2008-01-08_05/target-i386/helper.c > @@ -1710,6 +1710,79 @@ void helper_cpuid(void) > ECX = 0; > EDX = 0x2c307d; > break; > + case 4: > + /* cache info: needed for Core Duo compatibility */ > +/* From the Intel documentation: > +EAX: > + Bits 4-0: Cache Type** > + Bits 7-5: Cache Level (starts at 1) > + Bits 8: Self Initializing cache level (does not need SW initialization) > + Bits 9: Fully Associative cache Bits > + 13-10: Reserved Bits > + 25-14: Number of threads sharing this cache* Bits > + 31-26: Number of processor cores on this die (Multicore)* > +EBX: > + Bits 11-0: L = System Coherency Line Size* > + Bits 21-12: P = Physical Line partitions* > + Bits 31-22: W = Ways of associativity* > +ECX: > + Bits 31-0: S = Number of Sets* > +EDX: Reserved > + * Add one to the value in the register file to get the number. For example, > the number > + of processor cores is EAX[31:26]+1. > +** Cache Types fields > + 0 = Null - No more caches > + 1 = Data Cache > + 2 = Instruction Cache > + 3 = Unified Cache > + 31-4 = Reserved > +*/ > + > + switch (ECX) { > + case 0: // L1 cache info > +/* EAX = 3 // Unified Cache > + | (1 << 5) // L1 Cache > + | (1 << 8); // Self Initializing > + EBX = 63 // Line size = 64 bytes > + | (1022 << 12) // Partitions = 1024 bytes > + | (0 << 22); // Ways = 2 > + ECX = 0x3f; // One L1 Cache > + EDX = 0;*/ > + EAX = 0x0000123; > + EBX = 0x1c0003f; > + ECX = 0x000003f; > + EDX = 0x0000001; > + break; > + case 1: // L2 cache info > +/* EAX = 3 // Unified Cache > + | (2 << 5) // L2 Cache > + | (1 << 8); // Self Initializing > + EBX = 63 // Line size = 64 bytes > + | (1023 << 12) // Partitions = 1024 bytes > + | (0 << 22); // Ways = 512 > + ECX = 0; // One L2 Cache > + EDX = 0; > +*/ > + EAX = 0x0000122; > + EBX = 0x1c0003f; > + ECX = 0x000003f; > + EDX = 0x0000001; > + break; Why do you explain one set of values, and actually use something different? It confuses the untrained reader (me). Dan.