]> git.ipfire.org Git - thirdparty/gcc.git/blob - libvtv/testsuite/thunk_vtable_map_attack.cc
Commit the vtable verification feature.
[thirdparty/gcc.git] / libvtv / testsuite / thunk_vtable_map_attack.cc
1 #include <assert.h>
2 #include <signal.h>
3 #include <setjmp.h>
4 #include <stdio.h>
5
6 #include <iostream>
7 #include <fstream>
8
9 using std::ofstream;
10 using std::ifstream;
11 using std::ios;
12
13 struct A {
14 A():value(123) {}
15 int value;
16 virtual int access() { return this->value; }
17 };
18 struct B {
19 B():value(456) {}
20 int value;
21 virtual int access() { return this->value; }
22 };
23 struct C : public A, public B {
24 C():better_value(789) {}
25 int better_value;
26 virtual int access() { return this->better_value; }
27 };
28 struct D: public C {
29 D():other_value(987) {}
30 int other_value;
31 virtual int access() { return this->other_value; }
32 };
33
34 volatile static int signal_count = 0;
35
36 sigjmp_buf before_segv;
37
38 static void
39 handler(int sig, siginfo_t *si, void *unused)
40 {
41 /*
42 printf("Got SIGSEGV at address: 0x%lx\n",
43 (long) si->si_addr);
44 */
45
46 signal_count++;
47 /* You are not supposed to longjmp out of a signal handler but it seems
48 to work for this test case and it simplifies it */
49 siglongjmp(before_segv, 1);
50 /* exit(1); */
51 }
52
53 /* Access one of the vtable_map variables generated by this .o */
54 extern void * _ZN4_VTVI1BE12__vtable_mapE;
55
56 /* Access one of the vtable_map variables generated by libstdc++ */
57 extern void * _ZN4_VTVISt8ios_baseE12__vtable_mapE;
58
59 int use(B *b)
60 {
61 int ret;
62
63 ret = sigsetjmp(before_segv, 1);
64 if (ret == 0)
65 {
66 /* This should generate a segmentation violation. ie: at this point it should
67 be protected */
68 _ZN4_VTVI1BE12__vtable_mapE = 0;
69 }
70 assert(ret == 1 && signal_count == 1);
71
72 ret = sigsetjmp(before_segv, 1);
73 if (ret == 0)
74 {
75 /* Try to modify one of the vtable_map variables in the stdc++ library.
76 This should generate a segmentation violation. ie: at this point it
77 should be protected */
78 _ZN4_VTVISt8ios_baseE12__vtable_mapE = 0;
79 }
80 assert(ret == 1 && signal_count == 2);
81
82 return b->access();
83 }
84
85 void myread(std::istream * in)
86 {
87 char input_str[50] = "\0";
88 if (in->good())
89 (*in) >> input_str;
90 std::cout << input_str << std::endl;
91 delete in;
92 }
93
94 int main()
95 {
96 ifstream * infile = new ifstream("./thunk_vtable_map_attack.cpp");
97 myread(infile);
98
99 /* Set up handler for SIGSEGV. */
100 struct sigaction sa;
101 sa.sa_flags = SA_SIGINFO;
102 sigemptyset(&sa.sa_mask);
103 sa.sa_sigaction = handler;
104 if (sigaction(SIGSEGV, &sa, NULL) == -1)
105 assert(0);
106
107 C c;
108 assert(use(&c) == 789);
109
110 return 0;
111 }