Game Development Community

Why can't a function pointer be a function pointer?!

by Frank Carney · 12/16/2011 (6:15 am) · 5 comments

Learning how C++ works internally is a pain when you thought you solved something so elegantly...

So I think up this really cool thing where I can create a callback function and each object will store some unique data. You know the cool C++ features of storing data with your object. Then I go to actually setup the callback and come to find out that a pointer to a function is not the same as a pointer to a member function! Crap!!!

Now my elegant solution is dying because the internal API I want to use it with is designed around pointers to functions, not member functions. Darn it! I guess knowing there is a difference is important.

Oh, and if you think you are smart and want to do some type casting, think again: here. Yes, I was disappointed too. :)

About the author

I Started programming in HS and have never stopped. Now an 18 year vet of programming anything from assembler on a NES console to a nuclear waste processing system. If it can be programmed I may have tried to program it!


#1
12/16/2011 (6:19 am)
Did you think about function templates as alternative to function pointers for example?

And there are reasons why evil beings like me are not accepting C++ as a modern OO language. Its a large pile of more, less or less than less thought out 'stolen together OO features' on a language thats more like 10 languages with not one being fully featured.
#2
12/16/2011 (8:21 am)
member function pointers are like voodoo so be careful. I generally just concede and make my code work with regular function pointers.
#3
12/16/2011 (11:40 am)
@Marc,
No, because the console callback registration functions have to have regular function pointers. It is an API driving this. I just need to create an object to store a lookup to determine which object I need to talk to. I was trying for a more elegant method only to find I was trying to mix apples with oranges. My storage object was going to be the class that held the callback. So when the callback was executed it would automatically have a reference to the correct object. However, it does not work that way inside of C++.

@Tim,
Yep, after reading the information at the link I provided I have come to have more understanding of what is going on inside the C++ member function calls. The link described some neat things though. One of those was a method to get the compiler to tell you the type of any particular function. That is kind of a handy thing to be able to determine. Especially on foreign APIs.
#4
12/18/2011 (11:27 pm)
Frank,

If you aren't already aware Fast Delegate will help you out. It's far better than working with member/function pointers directly :)

At one point Torque had Fast Delegate in it, though I may be thinking of the old R&D engine.

T.

Edit: In case it's not obvious from the link, Fast Delegate will let you use delegates to both functions and methods with the same API. You'll have to change your function pointer based API to use the FastDelegate template instead, but it'll be worth it.
#5
12/19/2011 (3:36 am)
I was just looking at those articles and I cannot get my head around it. It looks like it creates function pointers that are incompatible with regular C function pointers. Unless I replace the entire representation of the function pointers in the T3D engine I cannot make use of that. That sounds like it could be scary to debug too!

Right now I am using direct pointers to C functions. Nothing in the middle. I don't see anything being faster than that. Now if the engine were based upon C++ methods for callbacks then it might be worth it.

Something to consider, if there was another mechanism for console callbacks that used objects then I could see doing similar to what you proposed. That would require getting into the compileEval.cpp code. Now, the compiled eval C++ code allow for multiple callback types: string, int, bool, etc. It may not be to hard to implement another type with separate registration functions, and separate calling methods. That might be an interesting tweak on the whole thing. That might just be a way to add more sophisticated callback mechanisms. It depends on how much pain it would cause on the registration side.

Hmmm, I think you may have got me thinking...