diff options
Diffstat (limited to 'board/MAI/bios_emulator/scitech/src/pm/cpuinfo.c')
-rw-r--r-- | board/MAI/bios_emulator/scitech/src/pm/cpuinfo.c | 808 |
1 files changed, 0 insertions, 808 deletions
diff --git a/board/MAI/bios_emulator/scitech/src/pm/cpuinfo.c b/board/MAI/bios_emulator/scitech/src/pm/cpuinfo.c deleted file mode 100644 index ac62e81c10..0000000000 --- a/board/MAI/bios_emulator/scitech/src/pm/cpuinfo.c +++ /dev/null @@ -1,808 +0,0 @@ -/**************************************************************************** -* -* SciTech OS Portability Manager Library -* -* ======================================================================== -* -* The contents of this file are subject to the SciTech MGL Public -* License Version 1.0 (the "License"); you may not use this file -* except in compliance with the License. You may obtain a copy of -* the License at http://www.scitechsoft.com/mgl-license.txt -* -* Software distributed under the License is distributed on an -* "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or -* implied. See the License for the specific language governing -* rights and limitations under the License. -* -* The Original Code is Copyright (C) 1991-1998 SciTech Software, Inc. -* -* The Initial Developer of the Original Code is SciTech Software, Inc. -* All Rights Reserved. -* -* ======================================================================== -* -* Language: ANSI C -* Environment: Any -* -* Description: Main module to implement the Zen Timer support functions. -* -****************************************************************************/ - -#include "ztimer.h" -#include "pmapi.h" -#include "oshdr.h" -#if !defined(__WIN32_VXD__) && !defined(__OS2_VDD__) && !defined(__NT_DRIVER__) -#include <stdio.h> -#include <string.h> -#endif - -/*----------------------------- Implementation ----------------------------*/ - -/* External Intel assembler functions */ -#ifdef __INTEL__ -/* {secret} */ -ibool _ASMAPI _CPU_haveCPUID(void); -/* {secret} */ -ibool _ASMAPI _CPU_check80386(void); -/* {secret} */ -ibool _ASMAPI _CPU_check80486(void); -/* {secret} */ -uint _ASMAPI _CPU_checkCPUID(void); -/* {secret} */ -uint _ASMAPI _CPU_getCPUIDModel(void); -/* {secret} */ -uint _ASMAPI _CPU_getCPUIDStepping(void); -/* {secret} */ -uint _ASMAPI _CPU_getCPUIDFeatures(void); -/* {secret} */ -uint _ASMAPI _CPU_getCacheSize(void); -/* {secret} */ -uint _ASMAPI _CPU_have3DNow(void); -/* {secret} */ -ibool _ASMAPI _CPU_checkClone(void); -/* {secret} */ -void _ASMAPI _CPU_readTimeStamp(CPU_largeInteger *time); -/* {secret} */ -void _ASMAPI _CPU_runBSFLoop(ulong iterations); -/* {secret} */ -ulong _ASMAPI _CPU_mulDiv(ulong a,ulong b,ulong c); -/* {secret} */ -void ZTimerQuickInit(void); -#define CPU_HaveMMX 0x00800000 -#define CPU_HaveRDTSC 0x00000010 -#define CPU_HaveSSE 0x02000000 -#endif - -#if defined(__SMX32__) -#include "smx/cpuinfo.c" -#elif defined(__RTTARGET__) -#include "rttarget/cpuinfo.c" -#elif defined(__REALDOS__) -#include "dos/cpuinfo.c" -#elif defined(__NT_DRIVER__) -#include "ntdrv/cpuinfo.c" -#elif defined(__WIN32_VXD__) -#include "vxd/cpuinfo.c" -#elif defined(__WINDOWS32__) -#include "win32/cpuinfo.c" -#elif defined(__OS2_VDD__) -#include "vdd/cpuinfo.c" -#elif defined(__OS2__) -#include "os2/cpuinfo.c" -#elif defined(__LINUX__) -#include "linux/cpuinfo.c" -#elif defined(__QNX__) -#include "qnx/cpuinfo.c" -#elif defined(__BEOS__) -#include "beos/cpuinfo.c" -#else -#error CPU library not ported to this platform yet! -#endif - -/*------------------------ Public interface routines ----------------------*/ - -/**************************************************************************** -REMARKS: -Read an I/O port location. -****************************************************************************/ -static uchar rdinx( - int port, - int index) -{ - PM_outpb(port,(uchar)index); - return PM_inpb(port+1); -} - -/**************************************************************************** -REMARKS: -Write an I/O port location. -****************************************************************************/ -static void wrinx( - ushort port, - ushort index, - ushort value) -{ - PM_outpb(port,(uchar)index); - PM_outpb(port+1,(uchar)value); -} - -/**************************************************************************** -REMARKS: -Enables the Cyrix CPUID instruction to properly detect MediaGX and 6x86 -processors. -****************************************************************************/ -static void _CPU_enableCyrixCPUID(void) -{ - uchar ccr3; - - PM_init(); - ccr3 = rdinx(0x22,0xC3); - wrinx(0x22,0xC3,(uchar)(ccr3 | 0x10)); - wrinx(0x22,0xE8,(uchar)(rdinx(0x22,0xE8) | 0x80)); - wrinx(0x22,0xC3,ccr3); -} - -/**************************************************************************** -DESCRIPTION: -Returns the type of processor in the system. - -HEADER: -ztimer.h - -RETURNS: -Numerical identifier for the installed processor - -REMARKS: -Returns the type of processor in the system. Note that if the CPU is an -unknown Pentium family processor that we don't have an enumeration for, -the return value will be greater than or equal to the value of CPU_UnkPentium -(depending on the value returned by the CPUID instruction). - -SEE ALSO: -CPU_getProcessorSpeed, CPU_haveMMX, CPU_getProcessorName -****************************************************************************/ -uint ZAPI CPU_getProcessorType(void) -{ -#if defined(__INTEL__) - uint cpu,vendor,model,cacheSize; - static ibool firstTime = true; - - if (_CPU_haveCPUID()) { - cpu = _CPU_checkCPUID(); - vendor = cpu & ~CPU_mask; - if (vendor == CPU_Intel) { - /* Check for Intel processors */ - switch (cpu & CPU_mask) { - case 4: cpu = CPU_i486; break; - case 5: cpu = CPU_Pentium; break; - case 6: - if ((model = _CPU_getCPUIDModel()) == 1) - cpu = CPU_PentiumPro; - else if (model <= 6) { - cacheSize = _CPU_getCacheSize(); - if ((model == 5 && cacheSize == 0) || - (model == 5 && cacheSize == 256) || - (model == 6 && cacheSize == 128)) - cpu = CPU_Celeron; - else - cpu = CPU_PentiumII; - } - else if (model >= 7) { - /* Model 7 == Pentium III */ - /* Model 8 == Celeron/Pentium III Coppermine */ - cacheSize = _CPU_getCacheSize(); - if ((model == 8 && cacheSize == 128)) - cpu = CPU_Celeron; - else - cpu = CPU_PentiumIII; - } - break; - default: - cpu = CPU_UnkIntel; - } - } - else if (vendor == CPU_Cyrix) { - /* Check for Cyrix processors */ - switch (cpu & CPU_mask) { - case 4: - if ((model = _CPU_getCPUIDModel()) == 4) - cpu = CPU_CyrixMediaGX; - else - cpu = CPU_UnkCyrix; - break; - case 5: - if ((model = _CPU_getCPUIDModel()) == 2) - cpu = CPU_Cyrix6x86; - else if (model == 4) - cpu = CPU_CyrixMediaGXm; - else - cpu = CPU_UnkCyrix; - break; - case 6: - if ((model = _CPU_getCPUIDModel()) <= 1) - cpu = CPU_Cyrix6x86MX; - else - cpu = CPU_UnkCyrix; - break; - default: - cpu = CPU_UnkCyrix; - } - } - else if (vendor == CPU_AMD) { - /* Check for AMD processors */ - switch (cpu & CPU_mask) { - case 4: - if ((model = _CPU_getCPUIDModel()) == 0) - cpu = CPU_AMDAm5x86; - else - cpu = CPU_AMDAm486; - break; - case 5: - if ((model = _CPU_getCPUIDModel()) <= 3) - cpu = CPU_AMDK5; - else if (model <= 7) - cpu = CPU_AMDK6; - else if (model == 8) - cpu = CPU_AMDK6_2; - else if (model == 9) - cpu = CPU_AMDK6_III; - else if (model == 13) { - if (_CPU_getCPUIDStepping() <= 3) - cpu = CPU_AMDK6_IIIplus; - else - cpu = CPU_AMDK6_2plus; - } - else - cpu = CPU_UnkAMD; - break; - case 6: - if ((model = _CPU_getCPUIDModel()) == 3) - cpu = CPU_AMDDuron; - else - cpu = CPU_AMDAthlon; - break; - default: - cpu = CPU_UnkAMD; - } - } - else if (vendor == CPU_IDT) { - /* Check for IDT WinChip processors */ - switch (cpu & CPU_mask) { - case 5: - if ((model = _CPU_getCPUIDModel()) <= 4) - cpu = CPU_WinChipC6; - else if (model == 8) - cpu = CPU_WinChip2; - else - cpu = CPU_UnkIDT; - break; - default: - cpu = CPU_UnkIDT; - } - } - else { - /* Assume a Pentium compatible Intel clone */ - cpu = CPU_Pentium; - } - return cpu | vendor | (_CPU_getCPUIDStepping() << CPU_steppingShift); - } - else { - if (_CPU_check80386()) - cpu = CPU_i386; - else if (_CPU_check80486()) { - /* If we get here we may have a Cyrix processor so we can try - * enabling the CPUID instruction and trying again. - */ - if (firstTime) { - firstTime = false; - _CPU_enableCyrixCPUID(); - return CPU_getProcessorType(); - } - cpu = CPU_i486; - } - else - cpu = CPU_Pentium; - if (!_CPU_checkClone()) - return cpu | CPU_Intel; - return cpu; - } -#elif defined(__ALPHA__) - return CPU_Alpha; -#elif defined(__MIPS__) - return CPU_Mips; -#elif defined(__PPC__) - return CPU_PowerPC; -#endif -} - -/**************************************************************************** -DESCRIPTION: -Returns true if the processor supports Intel MMX extensions. - -HEADER: -ztimer.h - -RETURNS: -True if MMX is available, false if not. - -REMARKS: -This function determines if the processor supports the Intel MMX extended -instruction set. - -SEE ALSO: -CPU_getProcessorType, CPU_getProcessorSpeed, CPU_have3DNow, CPU_haveSSE, -CPU_getProcessorName -****************************************************************************/ -ibool ZAPI CPU_haveMMX(void) -{ -#ifdef __INTEL__ - if (_CPU_haveCPUID()) - return (_CPU_getCPUIDFeatures() & CPU_HaveMMX) != 0; - return false; -#else - return false; -#endif -} - -/**************************************************************************** -DESCRIPTION: -Returns true if the processor supports AMD 3DNow! extensions. - -HEADER: -ztimer.h - -RETURNS: -True if 3DNow! is available, false if not. - -REMARKS: -This function determines if the processor supports the AMD 3DNow! extended -instruction set. - -SEE ALSO: -CPU_getProcessorType, CPU_getProcessorSpeed, CPU_haveMMX, CPU_haveSSE, -CPU_getProcessorName -****************************************************************************/ -ibool ZAPI CPU_have3DNow(void) -{ -#ifdef __INTEL__ - if (_CPU_haveCPUID()) - return _CPU_have3DNow(); - return false; -#else - return false; -#endif -} - -/**************************************************************************** -DESCRIPTION: -Returns true if the processor supports Intel KNI extensions. - -HEADER: -ztimer.h - -RETURNS: -True if Intel KNI is available, false if not. - -REMARKS: -This function determines if the processor supports the Intel KNI extended -instruction set. - -SEE ALSO: -CPU_getProcessorType, CPU_getProcessorSpeed, CPU_haveMMX, CPU_have3DNow, -CPU_getProcessorName -****************************************************************************/ -ibool ZAPI CPU_haveSSE(void) -{ -#ifdef __INTEL__ - if (_CPU_haveCPUID()) - return (_CPU_getCPUIDFeatures() & CPU_HaveSSE) != 0; - return false; -#else - return false; -#endif -} - -/**************************************************************************** -RETURNS: -True if the RTSC instruction is available, false if not. - -REMARKS: -This function determines if the processor supports the Intel RDTSC -instruction, for high precision timing. If the processor is not an Intel or -Intel clone CPU, this function will always return false. - -DESCRIPTION: -Returns true if the processor supports RDTSC extensions. - -HEADER: -ztimer.h - -RETURNS: -True if RTSC is available, false if not. - -REMARKS: -This function determines if the processor supports the RDTSC instruction -for reading the processor time stamp counter. - -SEE ALSO: -CPU_getProcessorType, CPU_getProcessorSpeed, CPU_haveMMX, CPU_have3DNow, -CPU_getProcessorName -****************************************************************************/ -ibool ZAPI CPU_haveRDTSC(void) -{ -#ifdef __INTEL__ - if (_CPU_haveCPUID()) - return (_CPU_getCPUIDFeatures() & CPU_HaveRDTSC) != 0; - return false; -#else - return false; -#endif -} - -#ifdef __INTEL__ - -#define ITERATIONS 16000 -#define SAMPLINGS 2 -#define INNER_LOOPS 400 - -/**************************************************************************** -REMARKS: -If processor does not support time stamp reading, but is at least a 386 or -above, utilize method of timing a loop of BSF instructions which take a -known number of cycles to run on i386(tm), i486(tm), and Pentium(R) -processors. -****************************************************************************/ -static ulong GetBSFCpuSpeed( - ulong cycles) -{ - CPU_largeInteger t0,t1,count_freq; - ulong ticks; /* Microseconds elapsed during test */ - ulong current; /* Variable to store time elapsed */ - int i,j,iPriority; - ulong lowest = (ulong)-1; - - iPriority = SetMaxThreadPriority(); - GetCounterFrequency(&count_freq); - for (i = 0; i < SAMPLINGS; i++) { - GetCounter(&t0); - for (j = 0; j < INNER_LOOPS; j++) - _CPU_runBSFLoop(ITERATIONS); - GetCounter(&t1); - current = t1.low - t0.low; - if (current < lowest) - lowest = current; - } - RestoreThreadPriority(iPriority); - - /* Compute frequency */ - ticks = _CPU_mulDiv(lowest,1000000,count_freq.low); - if ((ticks % count_freq.low) > (count_freq.low/2)) - ticks++; /* Round up if necessary */ - if (ticks == 0) - return 0; - return ((cycles*INNER_LOOPS)/ticks); -} - -#define TOLERANCE 1 - -/**************************************************************************** -REMARKS: -On processors supporting the Read Time Stamp opcode, compare elapsed -time on the High-Resolution Counter with elapsed cycles on the Time -Stamp Register. - -The inner loop runs up to 20 times oruntil the average of the previous -three calculated frequencies is within 1 MHz of each of the individual -calculated frequencies. This resampling increases the accuracy of the -results since outside factors could affect this calculation. -****************************************************************************/ -static ulong GetRDTSCCpuSpeed( - ibool accurate) -{ - CPU_largeInteger t0,t1,s0,s1,count_freq; - u64 stamp0, stamp1, ticks0, ticks1; - u64 total_cycles, cycles, hz, freq; - u64 total_ticks, ticks; - int tries,iPriority; - ulong maxCount; - - PM_set64_32(total_cycles,0); - PM_set64_32(total_ticks,0); - maxCount = accurate ? 600000 : 30000; - iPriority = SetMaxThreadPriority(); - GetCounterFrequency(&count_freq); - PM_set64(freq,count_freq.high,count_freq.low); - for (tries = 0; tries < 3; tries++) { - /* Loop until 100 ticks have passed since last read of hi-res - * counter. This accounts for overhead later. - */ - GetCounter(&t0); - t1.low = t0.low; - t1.high = t0.high; - while ((t1.low - t0.low) < 100) { - GetCounter(&t1); - _CPU_readTimeStamp(&s0); - } - - /* Loop until 30000 ticks have passed since last read of hi-res counter. - * This allows for elapsed time for sampling. For a hi-res frequency - * of 1MHz, this is about 0.03 of a second. The frequency reported - * by the OS dependent code should be tuned to provide a good - * sample period depending on the accuracy of the OS timers (ie: - * if the accuracy is lower, lower the frequency to spend more time - * in the inner loop to get better accuracy). - */ - t0.low = t1.low; - t0.high = t1.high; - while ((t1.low - t0.low) < maxCount) { - GetCounter(&t1); - _CPU_readTimeStamp(&s1); - } - - /* Find the difference during the timing loop */ - PM_set64(stamp0,s0.high,s0.low); - PM_set64(stamp1,s1.high,s1.low); - PM_set64(ticks0,t0.high,t0.low); - PM_set64(ticks1,t1.high,t1.low); - PM_sub64(cycles,stamp1,stamp0); - PM_sub64(ticks,ticks1,ticks0); - - /* Sum up the results */ - PM_add64(total_ticks,total_ticks,ticks); - PM_add64(total_cycles,total_cycles,cycles); - } - RestoreThreadPriority(iPriority); - - /* Compute frequency in Hz */ - PM_mul64(hz,total_cycles,freq); - PM_div64(hz,hz,total_ticks); - return PM_64to32(hz); -} - -#endif /* __INTEL__ */ - -/**************************************************************************** -DESCRIPTION: -Returns the speed of the processor in MHz. - -HEADER: -ztimer.h - -PARAMETERS: -accurate - True of the speed should be measured accurately - -RETURNS: -Processor speed in MHz. - -REMARKS: -This function returns the speed of the CPU in MHz. Note that if the speed -cannot be determined, this function will return 0. - -If the accurate parameter is set to true, this function will spend longer -profiling the speed of the CPU, and will not round the CPU speed that is -reported. This is important for highly accurate timing using the Pentium -RDTSC instruction, but it does take a lot longer for the profiling to -produce accurate results. - -SEE ALSO: -CPU_getProcessorSpeedInHz, CPU_getProcessorType, CPU_haveMMX, -CPU_getProcessorName -****************************************************************************/ -ulong ZAPI CPU_getProcessorSpeed( - ibool accurate) -{ -#if defined(__INTEL__) - /* Number of cycles needed to execute a single BSF instruction on i386+ - * processors. - */ - ulong cpuSpeed; - uint i; - static ulong intel_cycles[] = { - 115,47,43, - }; - static ulong cyrix_cycles[] = { - 38,38,52,52, - }; - static ulong amd_cycles[] = { - 49, - }; - static ulong known_speeds[] = { - 1000,950,900,850,800,750,700,650,600,550,500,450,433,400,350, - 333,300,266,233,200,166,150,133,120,100,90,75,66,60,50,33,20,0, - }; - - if (CPU_haveRDTSC()) { - cpuSpeed = (GetRDTSCCpuSpeed(accurate) + 500000) / 1000000; - } - else { - int type = CPU_getProcessorType(); - int processor = type & CPU_mask; - int vendor = type & CPU_familyMask; - if (vendor == CPU_Intel) - cpuSpeed = GetBSFCpuSpeed(ITERATIONS * intel_cycles[processor - CPU_i386]); - else if (vendor == CPU_Cyrix) - cpuSpeed = GetBSFCpuSpeed(ITERATIONS * cyrix_cycles[processor - CPU_Cyrix6x86]); - else if (vendor == CPU_AMD) - cpuSpeed = GetBSFCpuSpeed(ITERATIONS * amd_cycles[0]); - else - return 0; - } - - /* Now normalise the results given known processors speeds, if the - * speed we measure is within 2MHz of the expected values - */ - if (!accurate) { - for (i = 0; known_speeds[i] != 0; i++) { - if (cpuSpeed >= (known_speeds[i]-3) && cpuSpeed <= (known_speeds[i]+3)) { - return known_speeds[i]; - } - } - } - return cpuSpeed; -#else - return 0; -#endif -} - -/**************************************************************************** -DESCRIPTION: -Returns the speed of the processor in Hz. - -HEADER: -ztimer.h - -RETURNS: -Accurate processor speed in Hz. - -REMARKS: -This function returns the accurate speed of the CPU in Hz. Note that if the -speed cannot be determined, this function will return 0. - -This function is similar to the CPU_getProcessorSpeed function, except that -it attempts to accurately measure the CPU speed in Hz. This is used -internally in the Zen Timer libraries to provide accurate real world timing -information. This is important for highly accurate timing using the Pentium -RDTSC instruction, but it does take a lot longer for the profiling to -produce accurate results. - -SEE ALSO: -CPU_getProcessorSpeed, CPU_getProcessorType, CPU_haveMMX, -CPU_getProcessorName -****************************************************************************/ -ulong ZAPI CPU_getProcessorSpeedInHZ( - ibool accurate) -{ -#if defined(__INTEL__) - if (CPU_haveRDTSC()) { - return GetRDTSCCpuSpeed(accurate); - } - return CPU_getProcessorSpeed(false) * 1000000; -#else - return 0; -#endif -} - -/**************************************************************************** -DESCRIPTION: -Returns a string defining the speed and name of the processor. - -HEADER: -ztimer.h - -RETURNS: -Processor name string. - -REMARKS: -This function returns an English string describing the speed and name of the -CPU. - -SEE ALSO: -CPU_getProcessorType, CPU_haveMMX, CPU_getProcessorName -****************************************************************************/ -char * ZAPI CPU_getProcessorName(void) -{ -#if defined(__INTEL__) - static int cpu,speed = -1; - static char name[80]; - - if (speed == -1) { - cpu = CPU_getProcessorType(); - speed = CPU_getProcessorSpeed(false); - } - sprintf(name,"%d MHz ", speed); - switch (cpu & CPU_mask) { - case CPU_i386: - strcat(name,"Intel i386 processor"); - break; - case CPU_i486: - strcat(name,"Intel i486 processor"); - break; - case CPU_Pentium: - strcat(name,"Intel Pentium processor"); - break; - case CPU_PentiumPro: - strcat(name,"Intel Pentium Pro processor"); - break; - case CPU_PentiumII: - strcat(name,"Intel Pentium II processor"); - break; - case CPU_Celeron: - strcat(name,"Intel Celeron processor"); - break; - case CPU_PentiumIII: - strcat(name,"Intel Pentium III processor"); - break; - case CPU_UnkIntel: - strcat(name,"Unknown Intel processor"); - break; - case CPU_Cyrix6x86: - strcat(name,"Cyrix 6x86 processor"); - break; - case CPU_Cyrix6x86MX: - strcat(name,"Cyrix 6x86MX processor"); - break; - case CPU_CyrixMediaGX: - strcat(name,"Cyrix MediaGX processor"); - break; - case CPU_CyrixMediaGXm: - strcat(name,"Cyrix MediaGXm processor"); - break; - case CPU_UnkCyrix: - strcat(name,"Unknown Cyrix processor"); - break; - case CPU_AMDAm486: - strcat(name,"AMD Am486 processor"); - break; - case CPU_AMDAm5x86: - strcat(name,"AMD Am5x86 processor"); - break; - case CPU_AMDK5: - strcat(name,"AMD K5 processor"); - break; - case CPU_AMDK6: - strcat(name,"AMD K6 processor"); - break; - case CPU_AMDK6_2: - strcat(name,"AMD K6-2 processor"); - break; - case CPU_AMDK6_III: - strcat(name,"AMD K6-III processor"); - break; - case CPU_AMDK6_2plus: - strcat(name,"AMD K6-2+ processor"); - break; - case CPU_AMDK6_IIIplus: - strcat(name,"AMD K6-III+ processor"); - break; - case CPU_UnkAMD: - strcat(name,"Unknown AMD processor"); - break; - case CPU_AMDAthlon: - strcat(name,"AMD Athlon processor"); - break; - case CPU_AMDDuron: - strcat(name,"AMD Duron processor"); - break; - case CPU_WinChipC6: - strcat(name,"IDT WinChip C6 processor"); - break; - case CPU_WinChip2: - strcat(name,"IDT WinChip 2 processor"); - break; - case CPU_UnkIDT: - strcat(name,"Unknown IDT processor"); - break; - default: - strcat(name,"Unknown processor"); - } - if (CPU_haveMMX()) - strcat(name," with MMX(R)"); - if (CPU_have3DNow()) - strcat(name,", 3DNow!(R)"); - if (CPU_haveSSE()) - strcat(name,", SSE(R)"); - return name; -#else - return "Unknown"; -#endif -} |