• Advertisement

Archived

This topic is now archived and is closed to further replies.

Function pointer speed

This topic is 5323 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Is there any additional overhead for using a pointer to a function in comparison to using the function directly? I''m working on an access-path system for a 3d engine, where different functions are used depending on the user''s hardware config. So i am considering using pointers to functions rather than a standard switch: switch ( CurrentAccessPath ) { case GEFORCE: doThisFunction_GEFORCE(); break; case TNT2: doThisFunction_TNT2(); break; } Speed is essential. Thx for any help. "Standardize this..." _Adrenaline_@phayze.com

Share this post


Link to post
Share on other sites
Advertisement
Guest Anonymous Poster
Look at the architecture documentation for differences between a jump and an indirect jump. A function call to local functions is a jump to an immediate address. A pointer-to-function call is a jump to an indirect address, such as based off an offset in a register. The best answer you can get is to read up on the architectural documentation.

Share this post


Link to post
Share on other sites
The function pointer should be faster than the switch.
But, as always, profile, profile, profile.

edit:
Both versions involve an external variable (switch variable, pointer).
Switch involves either an indirect jump (jump table) or a series of conditional jumps (naive switch), then a direct call.
A call through a function pointer only involves an indirect call.

And ... C++ virtual functions are generally implemented with function pointers, not with switch statements


[ Start Here ! | How To Ask Smart Questions | Recommended C++ Books | C++ FAQ Lite | Function Ptrs | CppTips Archive ]
[ Header Files | File Format Docs | LNK2001 | C++ STL Doc | STLPort | Free C++ IDE | Boost C++ Lib | MSVC6 Lib Fixes ]


[edited by - Fruny on September 23, 2003 12:11:24 AM]

Share this post


Link to post
Share on other sites
Guest Anonymous Poster
Comparison and a jump table access versus a pointer dereference? Just offhand it''d seem like the function pointer will be a few cycles faster, but even if it wasn''t it''d be worthwhile to use it as opposed to a giant switch statement for the sake of code readability. Cycles here, cycles there. Worry about optimization after you profile, not before you have running code... and realize that if you''re agonizing over cycles before you''ve profiled, you''re wasting your time.

Share this post


Link to post
Share on other sites
Sorry if i wasn''t clear - this isnt for optimization purposes - im not profiling my system yet. I want to know which is faster now to save me the hassle of changing everything later. What this will do is provide multiple access paths to that a user with a ATI Raedon user will get every feature available to them, a GeForce user will get every feature available to them, while a TNT2 (oldskool) user can run it without those features, without having to check wether those features exist.

like:

void renderScene_ATI_Raedon();
void renderScene_NV_GeForce4();
void renderScene_NoFeatures();

the ATI and NV versions would have a lot more code than the NoFeatures version.

All of this is outside classes and not adhering to OO methodologies (i have my reasons, OO is good i know)

But anyway thanks for the help.

Share this post


Link to post
Share on other sites
Just my five,

A problem I had to deal with recently. If you call a function from your switch, the function call itself will be faster because it is known already at compile-time. Calling it from a function pointer means that you call it dynamically and you have to get it from somewhere in RAM first (Address of your function pointer). The call and push ops are gonna be the same afterwards. So the difference is a MOV.

Switch statements are evil as soon as they get bigger. I didn't check with the Disassembly of Visual Studio, but normally the value of CurrentAccessPath is loaded, and then a JZ to the function that you specified follows. If not, it will be decremented and JZ done with the next function. This is of course ok for a few cases, but for more than 10 definitely a bummer compared to what you actually try to do.


[edited by - sprinter_trueno on September 24, 2003 2:21:43 AM]

Share this post


Link to post
Share on other sites
If you are truly worried about the dereferencing time of a pointer, you have (A) too much free time or (B) too much painstaking worry over exceedingly low-level details.

While a short-range branch-to-sub can be faster than a full-address jump-to-sub, it will be at most a single hand of clocks faster to jump-to-literal-plus-program-offset as it will be to jump-to-register-plus-program-offset.

In essence, give me a break. Go profile, and find a function to optimize, instead of finding a single line of code to optimize.

Share this post


Link to post
Share on other sites
Guest Anonymous Poster
quote:
Original post by Fruny
The function pointer should be faster than the switch.
But, as always, profile, profile, profile.

edit:
Both versions involve an external variable (switch variable, pointer).
Switch involves either an indirect jump (jump table) or a series of conditional jumps (naive switch), then a direct call.
A call through a function pointer only involves an indirect call.

And ... C++ virtual functions are generally implemented with function pointers, not with switch statements

<hr><tt><font size="-1">[ <a href="http://www.gamedev.net/reference/start_here/">Start Here !</a> | <a href="http://www.catb.org/%7Eesr/faqs/smart-questions.html">How To Ask Smart Questions</a> | <a href="http://www.accu.org/bookreviews/public/reviews/0hr/">Recommended C++ Books</a> | <a href="http://www.parashift.com/c++-faq-lite/">C++ FAQ Lite</a> | <a href="http://www.function-pointer.org/">Function Ptrs</a> | <a href="http://search.freefind.com/find.html?id=8028742&m=0&p=0">CppTips Archive</a> ]<br>[ <a href="http://www.gamedev.net/reference/programming/features/orgfiles/">Header Files</a> | <a href="http://www.wotsit.org">File Format Docs</a> | <a href="http://msdn.microsoft.com/library/default.asp?url=/library/en-us/vccore/html/LNK2001.asp">LNK2001</a> | <a href="http://www.sgi.com/tech/stl/">C++ STL Doc</a> | <a href="http://www.stlport.org">STLPort</a> | <a href="http://www.bloodshed.net/devcpp.html">Free C++ IDE</a> | <a href="http://www.boost.org">Boost C++ Lib</a> | <a href="http://www.dinkumware.com/vc_fixes.html">MSVC6 Lib Fixes</a> ]</font></tt>

<SPAN CLASS=editedby>[edited by - Fruny on September 23, 2003 12:11:24 AM]</SPAN>


Well, virtual functions are implemented with the switch-to-function-pointer trick. An offset into a quasi-array of pointer-to-functions is essentially the same thing.

Share this post


Link to post
Share on other sites

  • Advertisement