Simple clock counter attempt:

Started by
10 comments, last by gimp 23 years, 9 months ago
    
#include "windows.h"

 __int64 GetClock()
{
	__int64 rslt;
	__asm
	{
		__emit 0x0f	// RDTSC - read time-stamp counter		__emit 0x31

		mov dword ptr [rslt],eax
		mov dword ptr [rslt+4],edx
	}
	return ( rslt );
}

void main(void)
{
	__int64 start;
	__int64 end;
	__int64 diff;

	start = GetClock();

	Sleep(1000);

	end = GetClock();

	diff = end - start;
}
    
I get an unhandled exception with this code on the RDTSC line. Any clues? I found a few other example of how to do this but they were like 3 pages long and really hard to follow...
Chris Brodie
Advertisement
Look through previous posts for the QueryPerformanceCounter and QueryPerformanceFrequency api''s. They have a very high resolution of 100''ths or 1000''s of a millisecond and is only two api calls! Work great, only down fall if that it only works on Pentiums or greater (No 486,386,etc..)

On the older machines use GetTickCount which you can also find info about with a search of threads. :-)

I''ve never used this rtsc clock so I don''t know how it works, but you can e-mail me assembler questions if you need too.

See ya,
Ben
__________________________Mencken's Law:"For every human problem, there is a neat, simple solution; and it's always wrong."
"Computers in the future may weigh no more than 1.5 tons."- Popular Mechanics, forecasting the relentless march of science in 1949
Yah it appears that you want to time a procedure and you''ll later replace the sleep 1000 with some real code and time how long it takes to execute. Is that right? If so definately use the PerformanceTimer functions. Otherwise tell me what your trying to do...
- Ben
__________________________Mencken's Law:"For every human problem, there is a neat, simple solution; and it's always wrong."
"Computers in the future may weigh no more than 1.5 tons."- Popular Mechanics, forecasting the relentless march of science in 1949
Yep thats exactly what I want to do, just time how long (in cycles) an event takes. My goal was eventially make a class that held values and did the math AND also subtract it''s own working time from the calculations.

In the end I''d like to say : "This loop takes 300 cycles and that one takes 400"
Chris Brodie
You have a Pentium, right?

See if this runs for you. I just compiled and ran it.

At the end, I had these values (on my P-II 450 w/ NT 4.0)

t_start = 214098140771222
t_end = 214098148610579
t_diff = 7839357

Here''s the whole program:

    #include "windows.h"#include "math.h"__int64 GetClock(){		__int64 rslt;	__asm	{		__emit 0x0f	// RDTSC - read time-stamp counter				__emit 0x31				mov dword ptr [rslt],eax				mov dword ptr [rslt+4],edx		}		return ( rslt );}int main(int argc, char* argv[]){		__int64 t_start;		__int64 t_end;		__int64 t_diff;		int n;	double d;	t_start = GetClock();			// Loop a bit	for(n = 1; n <= 81920; n++)	{		d = sqrt((double) n);	}	t_end = GetClock();	t_diff = t_end - t_start;	return(0);}    


Like I said.. Worked fine on my setup ; VC++ 6.0 Console Project.

// CHRIS
// CHRIS [win32mfc]
Just noticed.. Did you copy/paste your code right?
Your "__emit 0x31" comes after your comment -- on the same line. If that''s the case, it won''t get compiled and you''ll just have the 0x0F emit''d; missing the 0x31 will certainly cause problems.

// CHRIS
// CHRIS [win32mfc]
Thanks much. I might turn this in to a simple class that''ll manage the big ints. Does c++ have a 64bit integer thats isn''t platform specific? (I know LARGE_INTEGER is MS, not sure about __int64

Thanks..

PS : It''s interesting to not that if you drop the work and just call GetClock twice in a row the number of clock cycles that occurs in between doesn''t seem static. Some times you get ~200 then next you get ~220 etc. I was planning on just reducing the diff by the clocking overhead for a little more precision. Oh well...
Chris Brodie
If you're running under windows, there are context switches happening all the time. How much time is taken away from your app is up to the process scheduler.

The RDTSC loads the current value of the processor's time-stamp counter into the EDX:EAX registers. The time-stamp counter is contained in a 64-bit MSR. The high-order 32 bits of the MSR are loaded into the EDX register, and the low-order 32 bits are loaded into the EAX register. The processor increments the time-stamp counter MSR every clock cycle and resets it to 0 whenever the processor is reset. The time stamp disable (TSD) flag in register CR4 restricts the use of the RDTSC instruction. When the TSD flag is clear, the RDTSC instruction can be executed at any privilege level; when the flag is set, the instruction can only be executed at privilege level 0. The time-stamp counter can also be read with the RDMSR instruction, when executing at privilege level 0. The RDTSC instruction is not a serializing instruction. Thus, it does not necessarily wait until all previous instructions have been executed before reading the counter. Similarly, subsequent instructions may begin execution before the read operation is performed. This instruction was introduced into the Intel Architecture in the Pentium r processor.

// CHRIS


Edited by - win32mfc on July 14, 2000 1:01:36 AM
// CHRIS [win32mfc]
A gimp must make all possible mistakes before getting something right...

Never mind I was being an idiot again... I was running the app in debug mode. When I inlined the function and compiled as release I get a consistant 33 clocks... I can see how you example will still happen. What suprised me was that if you thread was to be suspended mid process I''s expect to see a massive or non at all, not small variances... anyway. I''m happy now
Chris Brodie
i tried the program above, and i saw something that i think is not normal. the result was correct in debug mode, but in release mode, it gave me always the same result: 33 clocks. why? i have the for loop between the two call of the function. and it works in debug mode....

the source is exactly same that win32mfc posted...

anyone know why???

cyberg- cyberg_coder@hotmail.com- http://members.xoom.com/cybergsoft

This topic is closed to new replies.

Advertisement