Skip to content

Commit f2c3c45

Browse files
committed
specs_odr_guard
1 parent 3c9eb69 commit f2c3c45

File tree

6 files changed

+106
-0
lines changed

6 files changed

+106
-0
lines changed

caster_odr_specs_odr_guard/car.cc

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
#include "engine.h"
2+
3+
namespace vehicles {
4+
5+
struct vehicle {};
6+
7+
struct car_specs {
8+
static constexpr unsigned unique_id = 10;
9+
int power() const { return 100; }
10+
};
11+
12+
} // namespace vehicles
13+
14+
namespace engine {
15+
16+
template <>
17+
struct specs<vehicles::vehicle> : vehicles::car_specs {};
18+
19+
} // namespace engine
20+
21+
int car_power() { return engine::power<vehicles::vehicle>(); }
Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
cl car.cc truck.cc vehicle_specs.cc /Fe"show.exe"
2+
.\show
3+
cl truck.cc car.cc vehicle_specs.cc /Fe"show.exe"
4+
.\show
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
set -e
2+
set -x
3+
clang++ -std=c++11 car.cc truck.cc vehicle_specs.cc && ./a.out
4+
clang++ -std=c++11 truck.cc car.cc vehicle_specs.cc && ./a.out
5+
rm a.out
Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
#pragma once
2+
3+
#include <stdio.h>
4+
5+
#include <typeinfo>
6+
7+
namespace engine {
8+
9+
template <typename T>
10+
struct specs {
11+
static constexpr unsigned unique_id = 0;
12+
int power() const { return 0; }
13+
};
14+
15+
namespace {
16+
17+
template <typename T>
18+
struct specs_odr_guard : specs<T> {
19+
static int translation_unit_local;
20+
};
21+
22+
template <typename T>
23+
int specs_odr_guard<T>::translation_unit_local = []() {
24+
fprintf(stdout, "MAKE_SPECS_ODR_GUARD %s %u\n", typeid(T).name(),
25+
specs<T>::unique_id);
26+
fflush(stdout);
27+
return 0;
28+
}();
29+
30+
} // namespace
31+
32+
template <typename T>
33+
using make_specs = specs_odr_guard<T>;
34+
35+
template <typename T>
36+
int power() {
37+
if (make_specs<T>::translation_unit_local) {
38+
}
39+
return make_specs<T>().power();
40+
}
41+
42+
} // namespace engine
Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
#include "engine.h"
2+
3+
namespace vehicles {
4+
5+
struct vehicle {};
6+
7+
struct truck_specs {
8+
static constexpr unsigned unique_id = 30;
9+
int power() const { return 300; }
10+
};
11+
12+
} // namespace vehicles
13+
14+
namespace engine {
15+
16+
template <>
17+
struct specs<vehicles::vehicle> : vehicles::truck_specs {};
18+
19+
} // namespace engine
20+
21+
int truck_power() { return engine::power<vehicles::vehicle>(); }
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
#include <iostream>
2+
3+
int car_power();
4+
int truck_power();
5+
6+
int main() {
7+
int pwr = 0;
8+
pwr = car_power();
9+
std::cout << "car power: " << pwr << std::endl;
10+
pwr = truck_power();
11+
std::cout << "truck power: " << pwr << std::endl;
12+
return 0;
13+
}

0 commit comments

Comments
 (0)