-
Notifications
You must be signed in to change notification settings - Fork 7
Expand file tree
/
Copy pathtest.cpp
More file actions
116 lines (86 loc) · 3.15 KB
/
test.cpp
File metadata and controls
116 lines (86 loc) · 3.15 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
#include <iostream>
#include "privablic.h"
// Demonstration
struct A
{
A() : x("struct private instance member has been accessed") {}
private:
char const* x;
static char const* y;
void f() {
std::cout << "struct private instance method has been accessed" << std::endl;
}
static void g() {
std::cout << "struct private static method has been accessed" << std::endl;
}
};
char const* A::y = "struct private static member has been accessed"; // static member init
// A stub type for A::x. Each distinct private member you need to
// access should have its own stub. Each stub should contain a
// nested ::type that is the corresponding pointer-to-member type.
struct A_x { typedef char const*(A::*type); };
// Explicit instantiation; the only place where it is legal to pass
// the address of a private member. Generates the static ::instance
// that in turn initializes member<Stub>::value.
template class private_member<A_x, &A::x>;
// This technique can also be used to access private static member variables.
struct A_y { typedef char const** type; };
template class private_member<A_y, &A::y>;
// This technique can also be used to access private instance methods
struct Af { typedef void(A::*type)(); };
template class private_method<Af, &A::f>;
// and to access private static methods.
struct Ag { typedef void(*type)(); };
template class private_method<Ag, &A::g>;
// with a class
class B {
public:
B() { x = 42; }
private:
int x;
static int y;
void f() { printf("class private instance method: %d\n", x); }
static void g() { printf("class private static method: %d\n", y ); }
};
int B::y = 42; // initialize static member
struct B_x { typedef int (B::*type); };
template class private_member<B_x, &B::x>;
struct B_y { typedef int *type; };
template class private_member<B_y, &B::y>;
struct Bf { typedef void(B::*type)(); };
template class private_method<Bf, &B::f>;
struct Bg { typedef void(*type)(); };
template class private_method<Bg, &B::g>;
int main()
{
A a;
// Use the member private member pointer
std::cout << a.*member<A_x>::value << std::endl;
// Use the member private static member pointer
std::cout << *member<A_y>::value << std::endl;
// Use the member private method member pointer
(a.*func<Af>::ptr)();
// Use the member private static method member pointer
(*func<Ag>::ptr)();
B b = B();
// Use the member private member pointer
printf("class private instance member: %d\n", b.*member<B_x>::value);
// Use the member private static member pointer
printf("class private static member: %d\n", *member<B_y>::value);
// Use the member private method member pointer
(b.*func<Bf>::ptr)();
// Use the member private static method member pointer
(*func<Bg>::ptr)();
};
/*
$ clang++ private_access.cpp -o private_access
$ ./private_access
struct private instance member has been accessed
struct private static member has been accessed
struct private instance method has been accessed
struct private static method has been accessed
class private instance member: 42
class private static member: 42
class private instance method: 42
class private static method: 42
*/