/* * [Pentium.java] * * Summary: Access Pentium/AMD specific features, e.g. RDTSC, CPUSERNO. * * Copyright: (c) 2005-2017 Roedy Green, Canadian Mind Products, http://mindprod.com * * Licence: This software may be copied and used freely for any purpose but military. * http://mindprod.com/contact/nonmil.html * * Requires: JDK 1.8+ * * Created with: JetBrains IntelliJ IDEA IDE http://www.jetbrains.com/idea/ * * Version History: * 1.1 2005-07-30 ANT build, consistent naming. * 1.2 2006-03-06 reformat with IntelliJ, add Javadoc. * 1.3 2007-06-03 add pad and icon * 1.4 2008-09-18 add cpuSerNo64 cpuSerNo96 display methods for serial number. * 1.5 2008-09-23 convert to jDK 1.5, deal with C++ missing DLLs. * 1.6 2012-12-11 add 64-bit support. */ package com.mindprod.pentium; import com.mindprod.common18.ST; import static java.lang.System.*; /** * Access Pentium/AMD specific features, e.g. RDTSC, CPUSERNO. *

* Uses JNI native C++/ASM code that only works on Windows. * * @author Roedy Green, Canadian Mind Products * @version 1.6 2012-12-11 add 64-bit support. * @since 2005 */ public final class Pentium { private static final int FIRST_COPYRIGHT_YEAR = 2005; /** * undisplayed copyright notice * * @noinspection UnusedDeclaration */ private static final String EMBEDDED_COPYRIGHT = "Copyright: (c) 2005-2017 Roedy Green, Canadian Mind Products, http://mindprod.com"; private static final String RELEASE_DATE = "2012-12-11"; /** * embedded version string. */ private static final String VERSION_STRING = "1.6"; /** * display a 64 bit serial number in hex in 4 groups of 4 hex digits * * @param serno serial number to display * * @return hex string equivalent. */ private static String display64BitSerialNumber( long serno ) { final int ms = ( int ) ( serno >>> 32 ); final int ls = ( int ) serno; final String mss = ST.toLZHexString( ms, 8 ); final String lss = ST.toLZHexString( ls, 8 ); final StringBuilder sb = new StringBuilder( 19 ); sb.append( mss.substring( 0, 4 ) ); sb.append( '-' ); sb.append( mss.substring( 4, 8 ) ); sb.append( '-' ); sb.append( lss.substring( 0, 4 ) ); sb.append( '-' ); sb.append( lss.substring( 4, 8 ) ); return sb.toString().toUpperCase(); } /** * display a 96 bit serial number in hex in 6 groups of 4 hex digits * * @param serno serial number to display, three 32 bit numbers msb in serno[0] * * @return hex string equivalent. */ private static String display96BitSerialNumber( int[] serno ) { final StringBuilder sb = new StringBuilder( 30 ); for ( int i = 0; i < 3; i++ ) { final String hex = ST.toLZHexString( serno[ i ], 8 ); sb.append( hex.substring( 0, 4 ) ); sb.append( '-' ); sb.append( hex.substring( 4, 8 ) ); sb.append( '-' ); } sb.setLength( 29 ); return sb.toString().toUpperCase(); } /** * Get the brand/model of the CPU. * * @return brand, e.g. "AMD Athlon(TM) XP 2000+" */ public static native String cpuIdBrand(); /** * Get the instruction set family of the CPU. * * @return family, possibly null if not Pentium. */ public static native int cpuIdFamily(); /** * Get the model of the CPU. * * @return model, possibly 0 if not Pentium. */ public static native int cpuIdModel(); /** * Get the stepping ID of the CPU. * * @return stepping ID. */ public static native int cpuIdStep(); /** * Get the vendor ID of the CPU. * * @return vendor, "GenuineIntel" for Intel chips, "AuthenticAMD" for AMD. */ public static native String cpuIdVendor(); /** * Get the 64-bit cpu Serial number for Pentium * * @return cpu serial number, possibly 0 if not Pentium. */ public static native long cpuSerNo64(); /** * Get the 96-bit cpu serial number for Xeon. * * @param select 0 for most significant 32 bits, 1 for middle, 2 for least significant. * * @return family, possibly 0 if not Xeon. */ public static native int cpuSerNo96( int select ); /** * test harness * * @param args not used */ public static void main( String[] args ) { // This needs to be done only once. It could go in a static init block. // For debugging it is better to put it here. // Get DLL loaded from somewhere on java.library path. // get DLL loaded from somewhere on java.library path. String dll = "pentium.x"; try { // load pentium.32.dlll or pentium.64.dll on path // arch is x86 or amd64 if ( System.getProperty( "os.arch" ).equals( "amd64" ) ) { dll = "pentium.64"; } else { dll = "pentium.32"; } // without .dll suffix System.loadLibrary( dll ); // if have troubles change this code to use load( // "E:\\com\\mindprod\\pentium\\pentium.32.dll" ); } catch ( Exception e ) { out.println( "Unable to load " + dll ); out.println( e.getMessage() ); System.exit( 1 ); } // if have troubles change this code to use load( // "E:\\com\\mindprod\\pentium\\nativepentium.dll" ); out.println( "cpuIdVendor:" + Pentium.cpuIdVendor() ); out.println( "cpuIdBrand:" + Pentium.cpuIdBrand() ); out.println( "cpuIdStep:" + ST.toLZHexString( Pentium.cpuIdStep(), 2 ) ); out.println( "cpuIdModel:" + ST.toLZHexString( Pentium.cpuIdModel(), 2 ) ); out.println( "cpuIdFamily:" + ST.toLZHexString( Pentium.cpuIdModel(), 2 ) ); out.println( "cpuSerNo64:" + display64BitSerialNumber( Pentium.cpuSerNo64() ) ); // collect Xeon serial number in three pieces. final int[] serno = new int[ 3 ]; serno[ 0 ] = Pentium.cpuSerNo96( 0 ); serno[ 1 ] = Pentium.cpuSerNo96( 1 ); serno[ 2 ] = Pentium.cpuSerNo96( 2 ); out.println( "cpuSerNo96:" + display96BitSerialNumber( serno ) ); out.println( "rdtsc:" + Long.toHexString( Pentium.rdtsc() ) ); } /** * Get the time stamp counter register with the RDTSC instruction giving the count of machine cycles since last * boot. This is very high resolution timer, with frequency matching the cpu clock crystal, not any defined time * unit. * * @return RDTSC Timestamp counter. */ public static native long rdtsc(); }