eepp
eepp

Reputation: 7585

How to have TU-specific function template instantiation?

Let's say:

In other words:

h.hpp:

template <typename T>
int f()
{
    return something + sizeof(T);
}

a.cpp:

#include "h.hpp"

struct S {
    int a;
    int b;
};

int aFunc()
{
    return f<S>();
}

b.cpp:

#include "h.hpp"

struct S {
    int w;
    int x;
    int y;
    int z;
};

int bFunc()
{
    return f<S>();
}

Here, within the same program, both aFunc() and bFunc() return the same value. This is because both structures are named S, and only one template function instantiation is kept.

My working solutions so far are:

  1. Name the structures differently.
  2. Make f() static.
  3. Make f() part of an anonymous namespace.
  4. Make both structures part of their own anonymous namespace.

Can you think of anything else to avoid this issue which only manifests at run time?

Upvotes: 0

Views: 116

Answers (1)

eepp
eepp

Reputation: 7585

I need to end this.

Considering the comments of n. 1.8e9-where's-my-share m. and VainMan: such a program is indeed ill-formed (ODR violation).

Therefore, the only legal solutions are those (1 and 4):

  • Name the structures differently.
  • Make both structures part of their own anonymous namespace.

I somehow stopped reading the One Definition Rule section at:

There can be more than one definition in a program of each of the following: class type, enumeration type, inline function, inline variable (since C++17), templated entity (template or member of template, but not full template specialization), as long as all of the following is true:

  • each definition appears in a different translation unit

But there's another important condition:

  • each definition consists of the same sequence of tokens (typically, appears in the same header file)

This is obviously not my case.

The outcome of not satisfying any of those conditions is:

Otherwise, the program is ill-formed, no diagnostic required.

Upvotes: 1

Related Questions