Speed of calling a function Delphi vs C++ - c++

I'm translating the C code from the handmadehero.org project to Delphi code. I ran into a performance issue on a specific piece:
Original:
inline real32
Win32GetSecondsElapsed(LARGE_INTEGER Start, LARGE_INTEGER End)
{
real32 Result = ((real32)(End.QuadPart - Start.QuadPart) /
(real32)GlobalPerfCountFrequency);
return(Result);
}
My version:
function Win32GetSecondsElapsed(Start, &End : LARGE_INTEGER): real32; inline;
begin
Result := (&End.QuadPart - Start.QuadPart) / GlobalPerfCountFrequency;
end;
After calling the sleep function there is this code to make sure that we hit the target frame rate:
SleepMilliSeconds = <some code that calcs how long to wait to hit target frame rate>
Sleep(SleepMilliSeconds);
real32 TestSecondsElapsedForFrame = Win32GetSecondsElapsed(LastCounter, Win32GetWallClock());
Assert(TestSecondsElapsedForFrame < TargetSecondsPerFrame);
If I use the same code (Only that it's the Delphi version), I get an assert error.
If I change the code to this:
TestSecondsElapsedForFrame := ((LastCounter.QuadPart - Win32GetWallClock().QuadPart) / GlobalPerfCountFrequency);
Assert(TestSecondsElapsedForFrame < TargetSecondsPerFrame);
The error goes away, so the call to the function in Delphi takes long enough to push me over the time allowed for the sleep to complete.
Does anyone know how I can fix this?
I have tried changing the parameters in the Win32GetSecondsElapsed to be passed as pointers, but it did not help.
I thought it may be because it's being passed by value and a copy needs to be made, but that is not it.
I think that the 'inline' directive is not taking effect.
I believe it should be possible for a Delphi application to be just as fast as a C application.

This function call is not causing any performance problems - the problems are in a completely different part of the code.
You're passing Win32GetWallClock() as End, and LastCounter as Start, so the function correctly computes
Win32GetWallClock().QuadPart - LastCounter.QuadPart
but the inline version computes
LastCounter.QuadPart - Win32GetWallClock().QuadPart
which is zero or negative.

Related

Correct implementation of a step-size controller for embedded Runge-Kutta methods

I have been trying to write a code in C++ for embedded Runge-Kutta methods (explicit and Rosenbrock for the moment). The idea is to keep the code simple and general so that one can pass their Butcher tableau (of any order) and just run it.
I have verified that the code works in general, but there are cases (when I have a very complicated system of 4 differential equations) where the stepsize control fails to adapt (I get constant stepsize or just wrong in general).
The stepsize control I use (I found it in this paper is:
//beta is some safety parameter
fac=beta;
if(Delta<=1) { //if current step is accepeted
if(delta_rej<=1){fac*=h/h_old; } //if previous step was rejected
fac*=std::pow(Delta, -0.65/( (LD) method.p + 1.) );
fac*=std::pow( delta_acc/Delta, 0.3/ ( (LD) method.p + 1. ) );
h_stop=true ; //this is used exit a loop inside which the stepsize control is called
}else{ //if current step is rejected
fac*=std::pow( Delta , -1./((LD) method.p +1. ) );
}
//don't allow h to increase or decrease very much
if(fac> fac_max){fac = fac_max;}
if(fac< fac_min){fac = fac_min;}
//update h
h=h*fac;
Here, h_old is the previously accepted stepsize, the step size of the current trial step is h.
Also, Delta [1] is the relative (local) error estimate for the current try (which the controller tries to make ~1), delta_rej is the Delta of the previous try, delta_acc is the Delta for the previous accepted step, and method.p is the order of the method (LD is a macro that can be double or long double).
I have tried using the simple version of this (i.e. just fac*=std:: pow( Delta, -1./((LD) method.p +1. ) );), but it seems that the previous one is a bit more stable.
For example, these are histograms I got that show the number of steps taken by my code vs scipy:
Explicit RKF,
Rosenbrock. As you can see, they are close, and the difference can be caused by the difference in the details of the implementation.
Having said that, I am still not sure, and what I really would like to know is whether I am using the controller correctly.
Thanks
[1]: This is the definition of Delta

Conversion of timespec for Windows 7 VS 2010

I am trying to build OpenVDB viewer for Windows 7 and bumped into this line of code:
secs = fabs(secs);
int isecs = int(secs);
struct timespec sleepTime = { isecs /*sec*/, int(1.0e9 * (secs - isecs)) /*nsec*/ };
nanosleep(&sleepTime, /*remainingTime=*/NULL);
Unfortunately, i dont know what exactly is the meaning of this code as i need to make it VS2010 compiler compatible in order to build it.
So, can i know what is the equivalent of this code or some other library that i can use to edit it easily??
Assuming secs is a float value giving the time the thread shall sleep in seconds, such as e.g.
float secs = 0.8312f;
You can replace that for the windows version with:
float secs = 0.8312f;
DWORD delay = static_cast<DWORD>(fabs(secs * 1000.0f));
Sleep(delay);
Possibly you could add some checks to this (such as if secs is not negative...).
In order to keep the main code base portable, you could create an extra module where you define your own portable sleep function, maybe with the signature void PortableSleep(float seconds);. Then, place in one .cpp file the Unix implementation, in another the win32 implementation and link accordingly.
What you also can do is using std::this_thread::sleep_for() if you like to waste time on figuring out how the <chrono> stuff works (VS lacks one feature, which makes it a bit harder to use).

Using Pow in C++ MinGW. Works hard coded but not with variables

This is hopefully a simple linker issue but I've spent hours searching and haven't moved forward in that time. I'm trying to use
#include <cmath>
double aA = 2;
double result = pow((double)2.0,(double)aA);
I get no error messages and it compiles without issue. But an unrelated grid I'm drawing with openGL doesn't display. If i substitute the aA for 2 then it displays the grid. Like
#include <cmath>
double aA = 2;
double result = pow((double)2.0,(double)2);
This outputs 4 as expected. The previous example outputs nothing. It's as if the program hangs but there are no errors.
This computation isn't used anywhere and in fact just sits in main (or anywhere else) and the variables are unique and are unused.
I'm using code::blocks and minGW GNU GCC compiler in Windows 7. -g -Wall - WExtra
Rendering with glew + freeglut and everything else works until i use a variable with pow.
I've tried every combination of casting I can think of and I've tried powf with the exact same result. I'm using sqrt and other functions so believe that the inclusion is working. I've also tried math.h but get the same problem.
I have never wished to see an error message from a compiler more so than I do right now.
So 1. Why am I not getting an error when it looks like its stopping the whole program in its tracks?
And 2. What have I missed to get pow() working with variables?
Update : After creating a new project and trying it out I have no issues so there must be something in my setup that's interfering. I'll keep experimenting. Thanks for the quick responses things sure move fast around here!
Update 2:
Very strange.
float aAs = 1.0;
float amplitudeA = (float)pow((float)2.,(float)aAs);
char str[50];
int test = (int) (amplitudeA);
sprintf (str, "out - %d", test);
MessageBox(NULL,str,NULL,NULL);
This outputs 2 in the message box. Then my grid draws and the program behaves. If i comment out only the message box like so:
float aAs = 1.0;
float amplitudeA = (float)pow((float)2.,(float)aAs);
char str[50];
int test = (int) (amplitudeA);
sprintf (str, "out - %d", test);
//MessageBox(NULL,str,NULL,NULL);
No drawing of my grid. What could be causing this?
char str[50];
int test = (int) (1);
sprintf (str, "out - %d", test);
MessageBox(NULL,str,NULL,NULL);
float aAs = 1.0;
float amplitudeA = (float)pow((float)2.,(float)aAs);
Swapping the message box over recreates the issue. No grid drawn. It's as if focus needs to be taken away from the program when I'm using a variable in pow. I'm completely baffled.
Another Update : I temporarily got around it by writing my own simple powerOf function. But now I'm having the same issue with the cos() function.
Can anyone tell me if there is something wrong with that image? This issue has to stem from incorrect linking. Is that what you would expect from hovering over coz in code::blocks with gcc?
This a error that occurs only when running through the program with a bad cos call. Interesting that I've been using cos for camera calculations since I started this app with no issue.
Error #667: UNADDRESSABLE ACCESS: reading 0x00000003-0x00000007 4 byte(s)
# 0 ntdll.dll!RtlImageNtHeader +0x124c (0x77ca43d0 <ntdll.dll+0x343d0>)
# 1 ntdll.dll!RtlImageNtHeader +0x422 (0x77ca35a7 <ntdll.dll+0x335a7>)
# 2 ntdll.dll!RtlImageNtHeader +0x30d (0x77ca3492 <ntdll.dll+0x33492>)
# 3 KERNEL32.dll!HeapFree +0x13 (0x775e14dd <KERNEL32.dll+0x114dd>)
# 4 atioglxx.dll!atiPPHSN +0x11afaa (0x66538f3b <atioglxx.dll+0xeb8f3b>)
# 5 atioglxx.dll!DrvSwapBuffers +0x33fb (0x6569b9cc <atioglxx.dll+0x1b9cc>)
# 6 atioglxx.dll!DrvSwapBuffers +0x3cad (0x6569c27e <atioglxx.dll+0x1c27e>)
# 7 atioglxx.dll!DrvSwapBuffers +0x7c57 (0x656a0228 <atioglxx.dll+0x20228>)
# 8 atioglxx.dll!DrvSwapBuffers +0x12c (0x656986fd <atioglxx.dll+0x186fd>)
# 9 atioglxx.dll!DrvValidateVersion +0x28 (0x65697c19 <atioglxx.dll+0x17c19>)
#10 OPENGL32.dll!wglSwapMultipleBuffers +0xc5d (0x66c8af0b <OPENGL32.dll+0x3af0b>)
#11 OPENGL32.dll!wglSwapMultipleBuffers +0xe45 (0x66c8b0f3 <OPENGL32.dll+0x3b0f3>)
Note: #0:00:05.233 in thread 3136
Note: instruction: mov 0x04(%ecx) -> %ecx
Solved. There was an uninitialized variable that was sitting at the bottom of the vertex buffer object I was using to draw the grid. For whatever reason feeding a variable to one of the math functions caused unexpected results in this buffer object.
Thanks to Angew an Kos for pointing me towards memory.

VST on XCode 4.6 - Plugin gives high output directly when loaded

I'm programming a Steinberg VST-Plugin in XCode 4.6.
I've already implemented a Highpass-filter which works correctly. Now I'm trying to do some nonlinear distortion with a quadratic function. After I implemented the few lines below and loaded the plugin into the host, I get immediatly an Output from the plugin - you can hear nothing, but the meter is up high.
I really can't imagine why. The processReplacing function where the math takes place should only be called when playing sound, not when the plugin is loaded. When I remove the few lines of code below, everything is okay and sounds right, so I assume it has nothing to do with the rest of the plugin-code.
The problem takes place in two hosts, so its probably not a VST-bug.
Has anybody ever experienced a similar problem?
Many Thanks,
Fabian
void Exciter::processReplacing(float** inputs, float** outputs, VstInt32 sampleFrames){
for(int i = 0; i < sampleFrames; i++) {
tempsample = inputs[0][i];
//Exciter - Transformation in positive region, quadratic distortion and backscaling
tempsample = tempsample + 1.0f;
tempsample = powf(tempsample, 2.0f);
tempsample = tempsample / 2.0f;
tempsample -= 1.0f;
//Mix-Knob: Dry/Wet ------------------------------------------------
outputs[0][i] = mix*(tempsample) + (1-mix)*inputs[0][i];
EDIT: I added logfile-outputs to each function and it occurs, that the processReplacing function is called permanently, not only when playback is turned on ... But why?
You pretty much answered the question yourself with your edit. processReplacing is called repeatedly. This is part of the VST specification.
VST plug-ins are targeted for real time effects processing. Don't confuse or misinterpret this as lookahead. By real time, I mean inserting the plug-in into a channel and playing an instrument while the DAW is recording. So you can see that in order to mitigate latency, the host is always sending the plug-in an audio buffer (whether it's silence or not).

Set Visual Studio (conditional) breakpoint on local variable value

I'm trying to debug a method which among other things, adds items to a list which is local to the method.
However, every so often the list size gets set to zero "midstream". I would like to set the debugger to break when the list size becomes zero, but I don't know how to, and would appreciate any pointers on how to do this.
Thanks.
Why not use conditional breakpoints?
http://blogs.msdn.com/saraford/archive/2008/06/17/did-you-know-you-can-set-conditional-breakpoints-239.aspx
in C#
if(theList.Count == 0){
//do something meaningless here .e.g.
int i = 1; // << set your breakpoint here
}
in VB.NET
If theList.Count = 0 Then
'do something meaningless here .e.g.
Dim i = 1; ' << set your breakpoint here
End If
For completeness sake, here's the C++ version:
if(theList->Count == 0){
//do something meaningless here .e.g.
int i = 1; // << set your breakpoint here
}
I can give a partial answer for Visual Studio 2005. If you open the "Breakpoints" window (Alt + F9) you get a list of breakpoints. Right-click on the breakpoint you want, and choose "Condition." Then put in the condition you want.
You have already got both major options suggested:
1. Conditional breakpoints
2. Code to check for the wrong value, and with a breakpoint if so happens
The first option is the easiest and best, but on large loops it is unfortunately really slow! If you loop 100's of thousands iterations the only real option is #2. In option #1 the cpu break into the debugger on each iteration, then it evaluates the condition and if the condition for breaking is false it just continiues execution of the program. This is slow when it happens thousands of times, it is actually slow if you loop just 1000 times (depending on hardware of course)
As I suspect you really want an "global" breakpoint condition that should break the program if a certain condition is met (array size == 0), unfortunately that does not exist to my knowledge. I have made a debugging function that checks the condition, and if it is true it does something meaningless that I have a breakpoint set to (i.e. option 2), then I call that function frequently where I suspect the original fails. When the system breaks you can use the call stack to identify the faulty location.