1
#include<iostream>

template<typename T>
class testClass {
  public:
  T a;
};

template<typename T>
void testFunc( void *a ) {
  testClass<T> *tempClass = reinterpret_cast<testClass<T> *>(a);
  tempClass->a++;
}

int main() {
  void (*foo)(void *);
  foo = testFunc<int>;
  testClass<int> a;
  a.a = 100;
  std::cerr << "Before = " << a.a << "\n";
  foo(&a);
  std::cerr << "After = " << a.a << "\n";
  return 0;
}

Can this template function testFunc be passed as function pointer to C functions safely ?? I am not clear how C++ is able to assign the correct memory address to the function pointer. The confusion is because I could not compile the same code in which I pass a class member function as function pointer argument.

muraly
  • 141
  • 1
  • 6

2 Answers2

2

The point with methods is that in order to access a method pointer, the compiler will ask you to provide the object calling this method, to auto-fill the this member when accessing the method.

Here, you mention a simple function pointer so you don't need to provide any object, so yes you can assume it's safe.

SeedmanJ
  • 444
  • 2
  • 8
0

Yes, it can be passed safely, and the answer (to "how does it store a pointer") is as follows.

Template functions are only instantiated when compiler encounters a particular call. In other words, if you just declare & define a template function but never use it, then there will be no functions generated and translated by the compiler. For example, in your snippet only one function is generated and translated into machine code (something like testFunc__int), and that function has a physical address in memory. And that's what you pass it to a C function.

The reason you couldn't pass a class member function is, like @SeedmanJ said, because member functions have this as the first argument (see here). Because of that, you actually need an instance of the class itself (see here).

I know I'm some 9 years (!) late to the party, but this is the first result in "can a template function be passed as function pointer" query, so I thought I'd add (:

gsarret
  • 160
  • 2
  • 7