Reputation: 875
GCC will not compile following code snippet (which in fact is correct behavior of GCC as it is conform to the standard C++ as I have learned already. VC++ however will compile.)
template<class T>
void CUDAMemory1D2DTextureAllocator<T>::allocateMemoryOnDevice()
{
m_pChannelDesc = cudaCreateChannelDesc<T>();
...
}
As i already found out by searching is, that one needs to tell the compiler that cudaCreateChannelDesc
is a template method. Otherwise it will try to
parse <
as a smaller than operator...
The following snippet shows that in an easy example:
template< typename G >
struct Test
{
template< typename T > T f() const;
};
template< typename G, typename T >
void g()
{
Test< G > t;
t.f< T >(); // ERROR: gcc won't compile that
t.template f< T >(); // OK: now gcc knows that f is a template method an treads the following angle brackets not as operators but as template brackets...
}
So far so good. Now my question is, how to do that in the above case, where the method I call is cudaCreateChannelDesc
which does not belong to any class or namespace?
Any advice or suggestion how to solve this situation are very welcome.
Thanks
Upvotes: 4
Views: 6679
Reputation: 18572
I'm assuming that cudaCreateChannel1Desc
is not a global or namespace function, because that should work, unless you forgot an include or a namespace resolution. And you do say it is a "method", i.e. a member function.
So, if it is a method of class CUDAMemory1D2DTextureAllocator
, then you should use this->template cudaCreateChannel1Desc<T>()
to call that method (which I have deduced is a method of a templated base class of CUDAMemory1D2DTextureAllocator
. Below is a compact illustration of what works and what doesn't in different situations (at least on gcc):
template <class G>
struct Base {
template< class T >
T h() const {
std::cout << "Hello World!" << std::endl;
};
};
template< class G >
struct Test : public Base<G>
{
template< class T >
T f() const {
std::cout << "Hello World!" << std::endl;
};
void callF() const {
f<G>(); //works!
this->f<G>(); //works!
h<G>(); //ERROR!
this->h<G>(); //ERROR!
this->template h<G>(); //works!
};
};
Upvotes: 2
Reputation: 1380
You can call it directly like: cudaCreateChannelDesc<T>()
if it doesn't belong to any class or namespace. Isn't it working like that?
Upvotes: 2
Reputation: 30969
Is the cudaCreateChannelDesc
function declared in some namespace that you have in scope? It appears that you might be having a problem with two-phase name lookup, which requires that some entities (like functions) referred to in templates need to be visible even before the template is instantiated. If you write a non-templated function in the same place as you definition of allocateMemoryOnDevice
and call cudaCreateChannelDesc
inside it, does the code compile? If not, you might be missing a #include
or a namespace qualification on cudaCreateChannelDesc
.
Upvotes: 1