CPUID 指令是一条重要的 x86 指令,用于 CPU 标识和特性检测。它允许软件查询 CPU 的详细信息,包括制造商、型号、特性以及扩展功能等。CPUID 指令在 Intel 和 AMD 的处理器上都被广泛支持。以下是使用 CPUID 指令的基本用法和示例代码:

使用 CPUID 指令的步骤:

  1. 设置 EAX 寄存器:将 EAX 寄存器设置为请求的功能代码。
  2. 执行 CPUID 指令:执行 cpuid 指令。
  3. 读取结果寄存器:从 EAX、EBX、ECX 和 EDX 寄存器读取返回的信息。

功能代码和返回信息:

  • 功能代码 0:获取最高支持的功能代码以及制造商 ID。
  • 功能代码 1:获取处理器信息和功能特性。
  • 功能代码 7:获取扩展功能。

示例代码(C 语言):

#include <stdio.h>

void cpuid(int code, int *a, int *b, int *c, int *d) {
    __asm__ volatile ("cpuid"
                      : "=a"(*a), "=b"(*b), "=c"(*c), "=d"(*d)
                      : "a"(code));
}

int main() {
    int eax, ebx, ecx, edx;
    
    // 功能代码 0
    cpuid(0, &eax, &ebx, &ecx, &edx);
    char vendor[13];
    *((int *)vendor) = ebx;
    *((int *)(vendor + 4)) = edx;
    *((int *)(vendor + 8)) = ecx;
    vendor[12] = '\0';
    printf("CPU Vendor: %s\n", vendor);
    
    // 功能代码 1
    cpuid(1, &eax, &ebx, &ecx, &edx);
    int family = (eax >> 8) & 0xF;
    int model = (eax >> 4) & 0xF;
    int stepping = eax & 0xF;
    printf("Family: %d, Model: %d, Stepping: %d\n", family, model, stepping);
    
    // 检查一些特性
    if (edx & (1 << 26))
        printf("SSE2 supported.\n");
    if (ecx & 1)
        printf("SSE3 supported.\n");
    
    return 0;
}

关键点:

  • Vendor ID:通过功能代码 0 返回的 EBX、ECX 和 EDX 寄存器获取 CPU 制造商 ID。
  • CPU 特性:通过功能代码 1 的返回值可以获取处理器家族、型号、步进信息,以及特性标志(如 SSE2、SSE3 支持)。

常见功能代码及其含义:

  • 0x80000000:获取扩展功能的最高支持值。
  • 0x80000001:获取扩展功能和特性。
  • 0x80000002 - 0x80000004:获取处理器名称(品牌字符串)。

CPUID 指令提供了对 CPU 的详细信息访问方式,对于编写硬件相关软件、优化程序性能或进行系统分析都非常有用。