Solved

Implementing timing control in loop

Posted on 2000-03-25
6
250 Views
Last Modified: 2010-04-02
I would like to iterate a loop, say once every few milliseconds. I tried using Sleep to do it. However, upon printing out the time using GetTickCount(), I notice that the timing interval is always rounded up to the next 10 milliseconds.

For example, if the code is something like the following.

for(i = 1; i <= 100; i++)
{
tickcount = GetTickCount();
printf("\n%lu",tickcount);
Sleep(25);
}

The printed result would be something like:
xxx12
xxx42
xxx72
and so on. That is, whether I put Sleep(21), Sleep(22) or whatever, the interval would never be accurate to the millisecond but would be rounded up to the next 10 milliseconds.

Is there any way to implement some timing control so that it is more accurate?


0
Comment
Question by:mych
6 Comments
 
LVL 3

Expert Comment

by:ufolk123
Comment Utility
Windows is not supposed to give you a real time response.As it is not a RTOS.There can be lot of dependencies on system load and priorties etc which can affect the exact timings you may be expecting.


0
 

Expert Comment

by:nisa
Comment Utility
Hi,
  Your question are too general as the timing (ie accuracy etc) depends on the systems used. What platform are using WINNT? WIN9x? or someother Oses? How about hardware ..? 386?486?Pentium.? or some other processors(because different hardware have different realtime clock).

Anyway, generally.. GetTickCount() will give u a value the way your system define 1 tick. Ie.. if your one tick is 10 milliseconds then your realtime clock is updated every 10 milliseconds (in every timer interrupt) and to increase the accuracy u would have to reduce it(but you have to pay penalty where timer interrupts occur more frequent and might slow down other processes).

Other things is that your method is *not* suitable for measuring accurate time granularity since, If you are in multitasking env. then your timing loop may get *preempted* by a higher prority tasks or interrupt. And the task may take cpu time longer than you expected. Also, in many system(ie WINNT, WIN9x) the interrupt lantency is resonably *high*.

The better way is to use a high resolution timer routines supplied by your system(if any :)) and used the elapsed time to increment your time. In this way, your timer will be *least* affected by problem mention above.

Hope this helps.

Best Regards,
Nisa.      
0
 

Author Comment

by:mych
Comment Utility
Hi Nina,
Can you give some examples of high resolution timer routines supplied by the system? By the way, I'm using WinNT on Pentium III.
0
Do You Know the 4 Main Threat Actor Types?

Do you know the main threat actor types? Most attackers fall into one of four categories, each with their own favored tactics, techniques, and procedures.

 
LVL 3

Expert Comment

by:ufolk123
Comment Utility
You can use the QueryPerformanceCounter() and QueryPerformanceFrequency() .Usage may be little bit differnt from that of SetTimer().
0
 

Accepted Solution

by:
nisa earned 50 total points
Comment Utility
Hi,


This Info was extracted from MSDN Library October 1999. *But* I have to remind you that it is virtual *impossible* to achive a *very* accurate timing on Normal WINNT (unless you are using Real Time Extension of WINNT or some other real time oSes).


High-Resolution Timer
----------------------

A counter is a general term used in programming to refer to an incrementing variable. Some systems include a high-resolution performance counter that provides high-resolution elapsed times.

If a high-resolution performance counter exists on the system, the QueryPerformanceFrequency function can be used to express the frequency, in counts per second. The value of the count is processor dependent. On some processors, for example, the count might be the cycle rate of the processor clock.

The QueryPerformanceCounter function retrieves the current value of the high-resolution performance counter (if one exists on the system). By calling this function at the beginning and end of a section of code, an application essentially uses the counter as a high-resolution timer. For example, suppose that QueryPerformanceFrequency indicates that the frequency of the high-resolution performance counter is 50,000 counts per second. If the application calls QueryPerformanceCounter immediately before and immediately after the section of code to be timed, the counter values might be 1500 counts and 3500 counts, respectively. These values would indicate that .04 seconds (2000 counts) elapsed while the code executed.

 
//-------------------------------------

QueryPerformanceFrequency
-------------------------

The QueryPerformanceFrequency function retrieves the frequency of the high-resolution performance counter, if one exists. The frequency cannot change while the system is running.

BOOL QueryPerformanceFrequency(
  LARGE_INTEGER *lpFrequency   // current frequency
);

Parameters
----------

lpFrequency

[out] Pointer to a variable that receives the current performance-counter frequency, in counts per second. If the installed hardware does not support a high-resolution performance counter, this parameter can be zero.
Return Values
If the installed hardware supports a high-resolution performance counter, the return value is nonzero.

If the function fails, the return value is zero. To get extended error information, call GetLastError. For example, if the installed hardware does not support a high-resolution performance counter, the function fails.

Requirements
  Windows NT/2000: Requires Windows NT 3.1 or later.
  Windows 95/98: Requires Windows 95 or later.
  Windows CE: Requires version 2.0 or later.
  Header: Declared in winbase.h; include windows.h.
  Library: Use kernel32.lib.


//-------------------------------------

QueryPerformanceCounter
-----------------------

The QueryPerformanceCounter function retrieves the current value of the high-resolution performance counter, if one exists.

BOOL QueryPerformanceCounter(
  LARGE_INTEGER *lpPerformanceCount   // counter value
);

Parameters
-----------
lpPerformanceCount

[out] Pointer to a variable that receives the current performance-counter value, in counts. If the installed hardware does not support a high-resolution performance counter, this parameter can be zero.
Return Values
If the installed hardware supports a high-resolution performance counter, the return value is nonzero.

If the function fails, the return value is zero. To get extended error information, call GetLastError. For example, if the installed hardware does not support a high-resolution performance counter, the function fails.

Remarks
On a multiprocessor machine, it should not matter which processor is called. However, you can get different results on different processors due to bugs in the BIOS or the HAL. To specify processor affinity for a thread, use the SetThreadAffinityMask function.

Requirements
  Windows NT/2000: Requires Windows NT 3.1 or later.
  Windows 95/98: Requires Windows 95 or later.
  Windows CE: Requires version 2.0 or later.
  Header: Declared in winbase.h; include windows.h.
  Library: Use kernel32.lib.



Best Regards,

Nisa.
0
 
LVL 1

Expert Comment

by:the_bikeman
Comment Utility
I'm not sure if this will be of any help, but if you are using gcc you can include time.h, and use the rawclock() functions.  It operates on 91.02 (rounded to 91) ticks per second.  Just a thought....

the_bikeman
0

Featured Post

Find Ransomware Secrets With All-Source Analysis

Ransomware has become a major concern for organizations; its prevalence has grown due to past successes achieved by threat actors. While each ransomware variant is different, we’ve seen some common tactics and trends used among the authors of the malware.

Join & Write a Comment

This tutorial is posted by Aaron Wojnowski, administrator at SDKExpert.net.  To view more iPhone tutorials, visit www.sdkexpert.net. This is a very simple tutorial on finding the user's current location easily. In this tutorial, you will learn ho…
This is a short and sweet, but (hopefully) to the point article. There seems to be some fundamental misunderstanding about the function prototype for the "main" function in C and C++, more specifically what type this function should return. I see so…
The goal of this video is to provide viewers with basic examples to understand and use pointers in the C programming language.
Video by: Grant
The goal of this video is to provide viewers with basic examples to understand and use nested-loops in the C programming language.

763 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

6 Experts available now in Live!

Get 1:1 Help Now