diff options
Diffstat (limited to 'private/ntos/nthals/haleagle/ppc/pxcalstl.c')
-rw-r--r-- | private/ntos/nthals/haleagle/ppc/pxcalstl.c | 184 |
1 files changed, 184 insertions, 0 deletions
diff --git a/private/ntos/nthals/haleagle/ppc/pxcalstl.c b/private/ntos/nthals/haleagle/ppc/pxcalstl.c new file mode 100644 index 000000000..bc8044575 --- /dev/null +++ b/private/ntos/nthals/haleagle/ppc/pxcalstl.c @@ -0,0 +1,184 @@ +/*++ + +Copyright (c) 1991-1993 Microsoft Corporation + Copyright 1994 MOTOROLA, INC. All Rights Reserved. This file + contains copyrighted material. Use of this file is restricted + by the provisions of a Motorola Software License Agreement. + +Module Name: + + pxcalstl.c + +Abstract: + + + This module implements the calibration of the stall execution HAL + service for a PowerPC system. + + +Author: + + David N. Cutler (davec) 26-Apr-1991 + Jim Wooldridge + Steve Johns (Motorola) + +Environment: + + Kernel mode only. + +Revision History: + +--*/ + +#include "halp.h" +#include "pxsystyp.h" + +// +// KeQueryPerformanceCounter & KeStallExecutionProcessor are called +// before Phase 0 initialization, so initialize it to a reasonable value. +// +ULONG HalpPerformanceFrequency = 80000000/16; +extern ULONG HalpClockCount; +extern ULONG HalpFullTickClockCount; + + +// +// Put all code for HAL initialization in the INIT section. It will be +// deallocated by memory management when phase 1 initialization is +// completed. +// + +#if defined(ALLOC_PRAGMA) + +#pragma alloc_text(INIT, HalpCalibrateStall) + +#endif + + + +ULONG +HalpCalibrateTBPStack( + VOID + ); + + +BOOLEAN +HalpCalibrateStall ( + VOID + ) + +/*++ + +Routine Description: + + This function calibrates the stall execution HAL service. + + N.B. This routine is only called during phase 1 initialization. + +Arguments: + + None. + +Return Value: + + A value of TRUE is returned if the calibration is successfully + completed. Otherwise a value of FALSE is returned. + +--*/ + +{ int i; + ULARGE_INTEGER BigNumber; + ULONG Variance; + ULONG BusSpeed; + static ULONG BusSpeeds [] = { + 25000000, + 33333333, + 40000000, + 41875000, + 50000000, + 55833333, + 60000000, + 66000000, + 66666666, + 67000000, + 75000000, + 80000000, + 83333333, + 83750000, + 90000000, + 99000000, + 100000000, + 111666666, + 120000000, + 132000000, + 133333332, + 134000000, + 150000000, + 160000000, + 166666666, + 167500000 + }; + + + + // + // Set initial scale factor + // + + PCR->StallScaleFactor = 1; + + // + // Compute the clock frequency of the Time Base & Decrementer + // + // It's possible for reads from the CMOS RTC to return odd results. + // For this reason, We can use a do-while loop, to ensure the calibration + // function is called at least once and is returning a reasonable value. + // + + do { + switch( HalpSystemType ) { + + case MOTOROLA_POWERSTACK: + HalpPerformanceFrequency = HalpCalibrateTBPStack(); + break; + + default: + case MOTOROLA_BIG_BEND: + HalpPerformanceFrequency = HalpCalibrateTB(); + break; + } + } while( HalpPerformanceFrequency < 1000000 ); + + // + // CPU bus runs at 4 times the DECREMENTER frequency + // + BusSpeed = HalpPerformanceFrequency * 4; + + // + // Choose the bus speed which is closest to calculated value. + // If the bus speed is not "close enough", then it may be + // a new speed which we don't know about. For this case + // we will leave the Performance Frequency alone. + // + for (i=0; i< (sizeof(BusSpeeds)/sizeof(ULONG)); i++) { + // + // We are going to allow for a 0.1% variation + // in calibrated frequency of the system bus clock. + // Calculate the variance as 1/2048 the frequency. + // + Variance = BusSpeeds[i] >> 11; + if ((BusSpeeds[i] - Variance < BusSpeed) && + (BusSpeeds[i] + Variance > BusSpeed)) { + HalpPerformanceFrequency = BusSpeeds[i] / 4; + break; + } + } + + // + // Initialize the system clock variables + // + HalpClockCount = (HalpPerformanceFrequency * (MAXIMUM_INCREMENT/10000)) / 1000; + HalpFullTickClockCount = HalpClockCount; + + return TRUE; +} |