java.lang.Object
freenet.support.CPUInformation.CPUID

public class CPUIDextends Object
Retrieves CPU details via the x86 CPUID instruction through a native JNI library (jcpuid).

This class provides low-level access to CPU identification and feature flags. It loads a platform-specific native library (libjcpuid.so / jcpuid.dll) that executes the CPUID assembly instruction and returns register values.

CPUID Register Layout (Leaf 1, EAX)

Bits 31:28  Reserved
Bits 27:20  Extended Family ID
Bits 19:16  Extended Model ID
Bits 15:12  Processor Type (Intel only; AMD reserved)
Bits 11:8   Base Family ID
Bits 7:4    Base Model ID
Bits 3:0    Stepping ID

Family/Model Computation

The actual (displayed) family and model are computed as follows:

  • Actual Family = Base Family + Extended Family (only when Base Family == 0xF for Intel; always for AMD)
  • Actual Model = Base Model + (Extended Model << 4) (only when Base Family == 0x6 or 0xF for Intel; always for AMD)

AMD Family/Microarchitecture Mapping

AMD Family/Microarchitecture Mapping
Family (hex)MicroarchitectureProducts
15 (0xF)K8 / HammerAthlon 64, Opteron
16 (0x10)K10Phenom, Athlon II
20 (0x14)BobcatOntario, Zacate
21 (0x15)Bulldozer familyFX, Opteron
22 (0x16)JaguarKabini, Temash
23 (0x17)Zen / Zen+ / Zen 2Ryzen 1000-3000, EPYC 7001-7002
25 (0x19)Zen 3 / Zen 4Ryzen 5000-8000, EPYC 7003-9004
26 (0x1A)Zen 5Ryzen 9000, EPYC 9005, Ryzen AI 300

AMD Family 19h (Zen 3/4) Model Ranges

0x00-0x0F  Milan/Chagall      (Zen 3)   - EPYC 7003, Threadripper 5000
0x10-0x1F  Stones/Storm Peak  (Zen 4)   - EPYC 9004, Threadripper 7000
0x20-0x2F  Vermeer            (Zen 3)   - Ryzen 5000 desktop
0x30-0x3F  Badami             (Zen 3)   - EPYC (internal)
0x40-0x4F  Rembrandt          (Zen 3+)  - Ryzen 6000 mobile
0x50-0x5F  Cezanne            (Zen 3)   - Ryzen 5000 APU
0x60-0x6F  Raphael            (Zen 4)   - Ryzen 7000 desktop (AM5)
0x70-0x77  Phoenix/HawkPoint1 (Zen 4)   - Ryzen 7040/8040 APU
0x78-0x7F  Phoenix2/HawkPoint2(Zen 4)   - Ryzen 8040 APU
0xA0-0xAF  Stones-Dense       (Zen 4)   - EPYC 4004/Siena

AMD Family 1Ah (Zen 5) Model Ranges

Sources: LLVM Host.cpp, Linux kernel amd.c, InstLatx64 CPUID dumps.

0x00-0x0F  Breithorn/Turin        (Zen 5)   - EPYC 9005 server
0x10-0x1F  Breithorn-Dense        (Zen 5)   - EPYC 9005 dense
0x20-0x2F  Strix Point            (Zen 5)   - Ryzen AI 300 mobile
0x30-0x37  Strix Point (2nd)      (Zen 5)   - Ryzen AI 300 mobile
0x38-0x3F  Strix Point (3rd)      (Zen 5)   - Ryzen AI 300 mobile
0x40-0x4F  Granite Ridge          (Zen 5)   - Ryzen 9000 desktop (AM5)
0x50-0x5F  Weisshorn              (Zen 6)   - NOT Zen 5!
0x60-0x6F  Krackan Point          (Zen 5)   - Ryzen AI 300 mobile
0x70-0x77  Sarlak/Strix Halo      (Zen 5)   - Ryzen AI Max 300
0xD0-0xD7  Annapurna              (Zen 5)   - Future EPYC

CPUID Brand String (Most Reliable Identification)

CPUID leaves 0x80000002-0x80000004 return a 48-byte ASCII brand string programmed by AMD/Intel into the CPU. This is the most reliable way to identify a specific CPU model, as model number ranges can overlap across product lines (e.g., model 0x44 is Granite Ridge desktop, not Strix Halo).

See Also:
  • Nested Class Summary

    Nested Classes
    Modifier and Type
    Class
    Description
    protected static class 
    Holds the four 32-bit register values (EAX, EBX, ECX, EDX) returned by a single CPUID instruction call.
  • Field Summary

    Fields
    Modifier and Type
    Field
    Description
    private static boolean
    Should basic success and failure info be dumped to stderr during initialization? This would otherwise use the Log component, but this makes it easier for other systems to reuse this class.
    private static int
    Version of the loaded jcpuid library.
    private static CPUID.CPUIDResult
    CPUID leaf 1 result cache.
    private static boolean
    did we load the native lib correctly?
    private static final boolean
    True on FreeBSD, not counting kFreeBSD.
    private static final boolean
    True on kFreeBSD.
    private static final boolean
    True on Linux.
    private static final boolean
    True on a Mac.
    private static final boolean
    True on NetBSD.
    private static final boolean
    True on OpenBSD.
    private static final boolean
    True on Solaris.
    private static final boolean
    True on Windows.
    private static final boolean
    True on an x86 CPU.
    private static final String
    The lower case name of the operating system.
  • Constructor Summary

    Constructors
    Constructor
    Description
    Constructs an instance that carries no per-instance state: every detection method here is static and reads process-global CPUID state.
  • Method Summary

    Modifier and Type
    Method
    Description
    private static CPUID.CPUIDResult
    doCPUID(int iFunction)
    Executes a CPUID instruction with the given function number and returns the register values.
    private static final boolean
    extractLoadAndCopy(String resourceName)
    Extract a single resource, copy it to a temp location in the file system, and attempt to load it.
    private static void
    extractReg(int reg, StringBuilder buf)
    Extracts up to 4 bytes from a CPUID register into a StringBuilder.
    private static int
    Get the jcpuid version
    (package private) static int
    Returns the Extended Family ID from CPUID leaf 1, EAX bits 27:20.
    (package private) static int
    Returns the Extended Model ID from CPUID leaf 1, EAX bits 19:16.
    (package private) static int
    Returns the Base Family ID from CPUID leaf 1, EAX bits 11:8.
    (package private) static int
    Returns the Base Model ID from CPUID leaf 1, EAX bits 7:4.
    (package private) static String
    Returns the CPU brand string from CPUID extended leaves 0x80000002-0x80000004.
    (package private) static int
    Returns the Stepping ID from CPUID leaf 1, EAX bits 3:0.
    (package private) static int
    Returns the Type field from CPUID leaf 1, EAX bits 15:12.
    (package private) static String
    Returns the 12-byte CPU vendor ID string from CPUID leaf 0.
    (package private) static int
    Return the ECX feature flags
    (package private) static int
    Return the EDX feature flags
    (package private) static int
    Return the EBX feature flags from CPUID leaf 7.
    (package private) static int
    Return the extended ECX feature flags
    (package private) static int
    There's almost nothing in here.
    (package private) static int
    Return the extended EDX feature flags from CPUID leaf 0x80000001.
    static CPUInfo
    Return a CPUInfo instance for the current CPU.
    static int
    Return the jcpuid version
    private static CPUID.CPUIDResult
    Returns cached CPUID leaf 1 result, performing the native call only once.
    private static final String
    64-bit only, jcpuid is not built for 32-bit platforms
    private static final String
    File name prefix of the native library for this OS.
    private static final String
    File name suffix of the native library for this OS.
    private static final String
    Resource name of the cpuid native library.
    private static final boolean
    Check all of the jars in the classpath for the jcpuid dll/so.
    private static final boolean
    Try loading it from an explicitly built jcpuid.dll / libjcpuid.so
    private static final void
    Do whatever we can to load up the native library.
    static void
    main(String[] args)
    Print the detected CPU details to stdout, for scripts and diagnostics.
    private static int
    Get the jbigi version, only available since jbigi version 3 Caller must catch Throwable

    Methods inherited from class Object

    clone, equals, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait
  • Field Details

    • _nativeOk

      private static boolean _nativeOk
      did we load the native lib correctly?
    • _jcpuidVersion

      private static int _jcpuidVersion
      Version of the loaded jcpuid library.
    • _doLog

      private static boolean _doLog
      Should basic success and failure info be dumped to stderr during initialization? This would otherwise use the Log component, but this makes it easier for other systems to reuse this class. Well, we really want to use Log so if you are one of those "other systems" then comment out the I2PAppContext usage below. Set to false if not in router context, so scripts using TrustedUpdate don't spew log messages. main(String[]) below overrides to true.
    • isX86

      private static final boolean isX86
      True on an x86 CPU.
    • isWindows

      private static final boolean isWindows
      True on Windows.
    • OS_NAME

      private static final String OS_NAME
      The lower case name of the operating system.
    • isLinux

      private static final boolean isLinux
      True on Linux.
    • isKFreebsd

      private static final boolean isKFreebsd
      True on kFreeBSD.
    • isFreebsd

      private static final boolean isFreebsd
      True on FreeBSD, not counting kFreeBSD.
    • isNetbsd

      private static final boolean isNetbsd
      True on NetBSD.
    • isOpenbsd

      private static final boolean isOpenbsd
      True on OpenBSD.
    • isSunos

      private static final boolean isSunos
      True on Solaris.
    • isMac

      private static final boolean isMac
      True on a Mac.
    • _leaf1Cache

      private static volatile CPUID.CPUIDResult _leaf1Cache
      CPUID leaf 1 result cache. CPUID leaf 1 (function 0x01) returns processor version information (family, model, stepping) and feature bits (SSE, AVX, etc.). This is called by nearly every method in this class, so caching eliminates ~8 redundant native JNI round-trips per CPU detection cycle.
  • Constructor Details

    • CPUID

      public CPUID()
      Constructs an instance that carries no per-instance state: every detection method here is static and reads process-global CPUID state.
  • Method Details

    • doCPUID

      private static CPUID.CPUIDResult doCPUID(int iFunction)
      Executes a CPUID instruction with the given function number and returns the register values.

      Common CPUID functions:

      • 0x00 - Highest basic function, vendor ID string
      • 0x01 - Family/model/stepping, feature flags (SSE, AVX, etc.)
      • 0x07 - Extended feature flags (AVX2, AVX-512, SHA, etc.)
      • 0x80000000 - Highest extended function
      • 0x80000001 - Extended feature flags (LZCNT, SSE4A, etc.)
      • 0x80000002-4 - CPU brand string (48 bytes ASCII)
      • 0x80000008 - Virtual/physical address sizes
      Parameters:
      iFunction - The CPUID function number (EAX value)
      Returns:
      Register values after execution
      Throws:
      UnsatisfiedLinkError - if native library not loaded
    • nativeJcpuidVersion

      private static int nativeJcpuidVersion()
      Get the jbigi version, only available since jbigi version 3 Caller must catch Throwable
      Returns:
      the version reported by the native jcpuid code
    • fetchJcpuidVersion

      private static int fetchJcpuidVersion()
      Get the jcpuid version
      Returns:
      0 if no jcpuid available, 2 if version not supported
    • getJcpuidVersion

      public static int getJcpuidVersion()
      Return the jcpuid version
      Returns:
      0 if no jcpuid available, 2 if version not supported
    • getLeaf1

      private static CPUID.CPUIDResult getLeaf1()
      Returns cached CPUID leaf 1 result, performing the native call only once.
      Returns:
      the cached leaf 1 result
    • getCPUVendorID

      static String getCPUVendorID()
      Returns the 12-byte CPU vendor ID string from CPUID leaf 0. The string is constructed from EBX:EDX:ECX (in that order).

      Known vendor strings:

      • "AuthenticAMD" - AMD
      • "GenuineIntel" - Intel
      • "CentaurHauls" - VIA/Centaur
      • "HygonGenuine" - Hygon (AMD-based Chinese JV)
      Returns:
      12-character vendor string, or empty string if native library not loaded
    • getCPUFamily

      static int getCPUFamily()
      Returns the Base Family ID from CPUID leaf 1, EAX bits 11:8.

      WARNING: This is the raw Base Family, NOT the computed family. For AMD CPUs with Base Family == 0xF (15), you must add getCPUExtendedFamily() to get the actual family. For other AMD families (17h, 19h, 1Ah), the extended family is always added to the base family to form the actual family.

      Returns:
      Base Family ID (0-15)
      See Also:
    • getCPUModel

      static int getCPUModel()
      Returns the Base Model ID from CPUID leaf 1, EAX bits 7:4.

      WARNING: This is the raw Base Model, NOT the computed model. For CPUs with Base Family == 0x6 or 0xF, you must add getCPUExtendedModel() << 4 to get the actual model. For AMD CPUs, the extended model is always applied when computing the actual model.

      Returns:
      Base Model ID (0-15)
      See Also:
    • getCPUExtendedModel

      static int getCPUExtendedModel()
      Returns the Extended Model ID from CPUID leaf 1, EAX bits 19:16.

      To compute the actual model for CPUs where Base Family is 6 or 0xF:

        actualModel = baseModel + (extendedModel << 4)
      

      For AMD CPUs, this is always added to the base model.

      Returns:
      Extended Model ID (0-15)
    • getCPUType

      static int getCPUType()
      Returns the Type field from CPUID leaf 1, EAX bits 15:12.
      Returns:
      the Type field, 0 through 15
    • getCPUExtendedFamily

      static int getCPUExtendedFamily()
      Returns the Extended Family ID from CPUID leaf 1, EAX bits 27:20.

      To compute the actual family when Base Family == 0xF:

        actualFamily = baseFamily + extendedFamily
      

      For AMD CPUs, this is always added to the base family.

      Returns:
      Extended Family ID (0-255)
    • getCPUStepping

      static int getCPUStepping()
      Returns the Stepping ID from CPUID leaf 1, EAX bits 3:0.
      Returns:
      the Stepping ID, 0 through 15
    • getEDXCPUFlags

      static int getEDXCPUFlags()
      Return the EDX feature flags
      Returns:
      the raw 32 bit feature flags from CPUID leaf 1, EDX
    • getECXCPUFlags

      static int getECXCPUFlags()
      Return the ECX feature flags
      Returns:
      the raw 32 bit feature flags from CPUID leaf 1, ECX
    • getExtendedECXCPUFlags

      static int getExtendedECXCPUFlags()
      Return the extended ECX feature flags
      Returns:
      the raw 32 bit feature flags from CPUID leaf 0x80000001, ECX
    • getExtendedEDXCPUFlags

      static int getExtendedEDXCPUFlags()
      Return the extended EDX feature flags from CPUID leaf 0x80000001.
      Returns:
      the raw 32 bit feature flags from CPUID leaf 0x80000001, EDX
    • getExtendedEBXFeatureFlags

      static int getExtendedEBXFeatureFlags()
      Return the EBX feature flags from CPUID leaf 7.
      Returns:
      the raw 32 bit feature flags from CPUID leaf 7, EBX
    • getExtendedECXFeatureFlags

      static int getExtendedECXFeatureFlags()
      There's almost nothing in here.
      Returns:
      the raw 32 bit feature flags from CPUID leaf 7, ECX
    • getCPUModelName

      static String getCPUModelName()
      Returns the CPU brand string from CPUID extended leaves 0x80000002-0x80000004.

      This is the most reliable way to identify a specific CPU model. The brand string is a 48-byte ASCII string programmed by AMD/Intel into the CPU. Examples:

      • "AMD Ryzen 9 9900X 12-Core Processor"
      • "Intel(R) Core(TM) i9-14900K"
      • "AMD EPYC 9754 128-Core Processor"

      IMPORTANT: This is preferred over model-based identification. AMD model number ranges overlap across product lines (e.g., model 0x44 is Granite Ridge desktop, but model ranges can be ambiguous). The brand string is always correct when available.

      Returns:
      CPU brand string, or null if unsupported or native library not loaded
    • extractReg

      private static void extractReg(int reg, StringBuilder buf)
      Extracts up to 4 bytes from a CPUID register into a StringBuilder. Stops at the first null byte (CPUID strings are null-terminated).
      Parameters:
      reg - 32-bit register value (little-endian byte order)
      buf - the buffer the four decoded characters are appended to
    • getInfo

      public static CPUInfo getInfo() throws UnknownCPUException
      Return a CPUInfo instance for the current CPU.

      Detects the CPU vendor via CPUID leaf 0, then returns the appropriate implementation:

      Returns:
      CPUInfo for the detected CPU type
      Throws:
      UnknownCPUException - if native library not loaded, not x86, or unknown vendor
    • main

      public static void main(String[] args)
      Print the detected CPU details to stdout, for scripts and diagnostics.
      Parameters:
      args - currently unused; the CPU details come from the native library
    • loadNative

      private static final void loadNative()

      Do whatever we can to load up the native library. If it can find a custom built jcpuid.dll / libjcpuid.so, it'll use that. Otherwise it'll try to look in the classpath for the correct library (see loadFromResource). If the user specifies -Djcpuid.enable=false it'll skip all of this.

    • loadGeneric

      private static final boolean loadGeneric()

      Try loading it from an explicitly built jcpuid.dll / libjcpuid.so

      The file name must be (e.g. on linux) libjcpuid-x86_64-linux.so.
      Returns:
      true if it was loaded successfully, else false
    • loadFromResource

      private static final boolean loadFromResource()

      Check all of the jars in the classpath for the jcpuid dll/so. This file should be stored in the resource in the same package as this class.

      This is a pretty ugly hack, using the general technique illustrated by the onion FEC libraries. It works by pulling the resource, writing out the byte stream to a temporary file, loading the native library from that file. We then attempt to copy the file from the temporary dir to the base install dir, so we don't have to do this next time - but we don't complain if it fails, so we transparently support read-only base dirs.

      Only 64-bit jcpuid libraries are shipped.
      Returns:
      true if it was loaded successfully, else false
    • extractLoadAndCopy

      private static final boolean extractLoadAndCopy(String resourceName)
      Extract a single resource, copy it to a temp location in the file system, and attempt to load it. If the load succeeds, copy it to the installation directory. Return value reflects only load success - copy will fail silently.
      Parameters:
      resourceName - the classpath resource holding the native library to extract, load and copy
      Returns:
      true if it was loaded successfully, else false.
    • getResourceName

      private static final String getResourceName()
      Resource name of the cpuid native library.
      Returns:
      non-null
    • getLibraryPrefix

      private static final String getLibraryPrefix()
      File name prefix of the native library for this OS.
      Returns:
      the prefix, empty if none
    • getLibraryMiddlePart

      private static final String getLibraryMiddlePart()
      64-bit only, jcpuid is not built for 32-bit platforms
      Returns:
      the platform-specific library name, e.g. jcpuid-x86_64-linux
    • getLibrarySuffix

      private static final String getLibrarySuffix()
      File name suffix of the native library for this OS.
      Returns:
      the suffix, empty if none