コード例 #1
0
        public void Start()
        {
            // Calling start on a running Stopwatch is a no-op.

            if (!isRunning)
            {
                startTimeStamp = GetTimestamp();
                if (CPUTimeIsAvailable)
                {
                    //Remember the Thread ID, processor number & CurrentMHz
                    timerStartThreadHandle = Win32.GetCurrentThread();
                    timerStartCPUID        = Win32.GetCurrentProcessorNumber();
                    PROCESSOR_POWER_INFORMATION thisppi;
                    thisppi = CPUPowerWrapper.GetCurrentPowerInfoforProcessor();
                    timerStartCurrentMHz = thisppi.CurrentMhz;
                    timerEndCurrentMHz   = thisppi.CurrentMhz;
                    startCPUcycles       = GetCPUCycles(); //CPU Cycles consumed by the thread up to this point
                    elapsedCPUThisPeriod = 0;
                }
                isRunning = true;
            }
        }
コード例 #2
0
        public void Stop()
        {
            // Calling stop on a stopped Stopwatch is a no-op.
            if (isRunning)
            {
                long endTimeStamp = 0;
                endTimeStamp = GetTimestamp();

                if (CPUTimeIsAvailable)
                {
                    timerEndThreadHandle = Win32.GetCurrentThread();
                    long endCPUcycles = GetCPUCycles(); //Get CPU Cycles first

                    if (timerEndThreadHandle != timerStartThreadHandle)
                    {
                        threadSwitchOccurred = true; //A thread switch is a problem, since CPU Cycles are accumulated
                        endCPUcycles         = 0;    // at the thread level
                        startCPUcycles       = 0;
                    }
                    else
                    {
                        if (endCPUcycles > startCPUcycles)
                        {
                            elapsedCPUThisPeriod = endCPUcycles - startCPUcycles;
                            elapsedCPU          += elapsedCPUThisPeriod;
                        }
                        //How likely is it for the CPU time accumulator to wrap???
                        else
                        {
                            elapsedCPU     = 0;
                            endCPUcycles   = 0;
                            startCPUcycles = 0;
                        }
                    }
                }

                long elapsedThisPeriod = endTimeStamp - startTimeStamp;
                elapsed  += elapsedThisPeriod;
                isRunning = false;
                if (elapsed < 0)
                {
                    // When measuring small time periods the StopWatch.Elapsed*
                    // properties can return negative values.  This is due to
                    // bugs in the basic input/output system (BIOS) or the hardware
                    // abstraction layer (HAL) on machines with variable-speed CPUs
                    // (e.g. Intel SpeedStep).

                    elapsed = 0;
                }

                if (CPUTimeIsAvailable && elapsedCPU > 0)
                {
                    timerEndCPUID = Win32.GetCurrentProcessorNumber();
                    if (timerEndCPUID != timerStartCPUID)
                    {
                        // Exposed as the FinishedOnDifferentProcessor property
                        // Stopwatch cannot detect context switches in general,
                        // but we do know at least one context switch occurred in this case
                        //
                        cpuSwitchOccurred = true;
                    }
                    PROCESSOR_POWER_INFORMATION thisppi = CPUPowerWrapper.GetCurrentPowerInfoforProcessor();
                    timerEndCurrentMHz = thisppi.CurrentMhz;
                    timerEndMaxMHz     = thisppi.MaxMhz;
                    if (timerStartCurrentMHz != timerEndCurrentMHz)     // CPU speed change detected
                    {
                        // Exposed as the PowerManagementChangeOccurred property
                        // so long as the rdtsc is constant across power management events,
                        // this is no cause for concern
                        cpuspeedChangeOccurred = true;
                    }
                }
            }
        }