t_static_destructor.sh revision 1.5 1 # $NetBSD: t_static_destructor.sh,v 1.5 2022/06/12 08:55:36 skrll Exp $
2 #
3 # Copyright (c) 2017 The NetBSD Foundation, Inc.
4 # All rights reserved.
5 #
6 # This code is derived from software contributed to The NetBSD Foundation
7 # by Kamil Rytarowski.
8 #
9 # Redistribution and use in source and binary forms, with or without
10 # modification, are permitted provided that the following conditions
11 # are met:
12 # 1. Redistributions of source code must retain the above copyright
13 # notice, this list of conditions and the following disclaimer.
14 # 2. Redistributions in binary form must reproduce the above copyright
15 # notice, this list of conditions and the following disclaimer in the
16 # documentation and/or other materials provided with the distribution.
17 #
18 # THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
19 # ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
20 # TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
21 # PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
22 # BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
23 # CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
24 # SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
25 # INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
26 # CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
27 # ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
28 # POSSIBILITY OF SUCH DAMAGE.
29 #
30
31 atf_test_case static_destructor
32 static_destructor_head() {
33 atf_set "descr" "compile and run \"hello world\""
34 atf_set "require.progs" "c++"
35 }
36
37 atf_test_case static_destructor_profile
38 static_destructor_profile_head() {
39 atf_set "descr" "compile and run \"hello world\" with profiling option"
40 atf_set "require.progs" "c++"
41 }
42
43 atf_test_case static_destructor_static
44 static_destructor_static_head() {
45 atf_set "descr" "compile and run \"hello world\" with static option"
46 atf_set "require.progs" "c++"
47 }
48
49 atf_test_case static_destructor_pic
50 static_destructor_pic_head() {
51 atf_set "descr" "compile and run PIC \"hello world\""
52 atf_set "require.progs" "c++"
53 }
54
55 atf_test_case static_destructor_pic_32
56 static_destructor_pic_32_head() {
57 atf_set "descr" "compile and run 32-bit PIC \"hello world\""
58 atf_set "require.progs" "c++"
59 }
60
61 atf_test_case static_destructor_pic_profile
62 static_destructor_pic_profile_head() {
63 atf_set "descr" "compile and run PIC \"hello world\" with profiling option"
64 atf_set "require.progs" "c++"
65 }
66
67 atf_test_case static_destructor_pic_profile_32
68 static_destructor_pic_profile_32_head() {
69 atf_set "descr" "compile and run 32-bit PIC \"hello world\" with profiling option"
70 atf_set "require.progs" "c++"
71 }
72
73 atf_test_case static_destructor_profile_32
74 static_destructor_profile_32_head() {
75 atf_set "descr" "compile and run 32-bit \"hello world\" with profiling option"
76 atf_set "require.progs" "c++"
77 }
78
79 atf_test_case static_destructor_pie
80 static_destructor_pie_head() {
81 atf_set "descr" "compile and run position independent (PIE) \"hello world\""
82 atf_set "require.progs" "c++"
83 }
84
85 atf_test_case static_destructor32
86 static_destructor32_head() {
87 atf_set "descr" "compile and run \"hello world\" for/in netbsd32 emulation"
88 atf_set "require.progs" "c++ file diff cat"
89 }
90
91 static_destructor_body() {
92 cat > test.cpp << EOF
93 #include <iostream>
94 struct A {
95 int i;
96 A(int i):i(i){std::cout << "CTOR A" << std::endl;}
97 ~A() {std::cout << "DTOR A:" << i << std::endl;}
98 };
99 struct B {
100 A *m_a;
101 B(){static A s_a(10);m_a=&s_a;std::cout << "CTOR B" << std::endl;}
102 ~B(){std::cout << "DTOR B:" << (*m_a).i << std::endl;(*m_a).i = 20;}
103 };
104 int main(void) {struct B b;return 0;}
105 EOF
106 atf_check -s exit:0 -o ignore -e ignore c++ -o hello test.cpp
107 atf_check -s exit:0 -o inline:"CTOR A\nCTOR B\nDTOR B:10\nDTOR A:20\n" ./hello
108 }
109
110 static_destructor_profile_body() {
111 cat > test.cpp << EOF
112 #include <iostream>
113 struct A {
114 int i;
115 A(int i):i(i){std::cout << "CTOR A" << std::endl;}
116 ~A() {std::cout << "DTOR A:" << i << std::endl;}
117 };
118 struct B {
119 A *m_a;
120 B(){static A s_a(10);m_a=&s_a;std::cout << "CTOR B" << std::endl;}
121 ~B(){std::cout << "DTOR B:" << (*m_a).i << std::endl;(*m_a).i = 20;}
122 };
123 int main(void) {struct B b;return 0;}
124 EOF
125 atf_check -s exit:0 -static -o ignore -e ignore c++ -pg -o hello test.cpp
126 atf_check -s exit:0 -o inline:"CTOR A\nCTOR B\nDTOR B:10\nDTOR A:20\n" ./hello
127 }
128
129 static_destructor_profile_32_body() {
130 # check whether this arch is 64bit
131 if ! c++ -dM -E - < /dev/null | fgrep -q _LP64; then
132 atf_skip "this is not a 64 bit architecture"
133 fi
134 if ! c++ -m32 -dM -E - < /dev/null 2>/dev/null > ./def32; then
135 atf_skip "c++ -m32 not supported on this architecture"
136 else
137 if fgrep -q _LP64 ./def32; then
138 atf_fail "c++ -m32 does not generate netbsd32 binaries"
139 fi
140 fi
141
142 cat > test.cpp << EOF
143 #include <iostream>
144 struct A {
145 int i;
146 A(int i):i(i){std::cout << "CTOR A" << std::endl;}
147 ~A() {std::cout << "DTOR A:" << i << std::endl;}
148 };
149 struct B {
150 A *m_a;
151 B(){static A s_a(10);m_a=&s_a;std::cout << "CTOR B" << std::endl;}
152 ~B(){std::cout << "DTOR B:" << (*m_a).i << std::endl;(*m_a).i = 20;}
153 };
154 int main(void) {struct B b;return 0;}
155 EOF
156 atf_check -s exit:0 -static -o ignore -e ignore c++ -m32 -pg -o hello test.cpp
157 atf_check -s exit:0 -o inline:"CTOR A\nCTOR B\nDTOR B:10\nDTOR A:20\n" ./hello
158 }
159
160
161 static_destructor_static_body() {
162 cat > test.cpp << EOF
163 #include <iostream>
164 struct A {
165 int i;
166 A(int i):i(i){std::cout << "CTOR A" << std::endl;}
167 ~A() {std::cout << "DTOR A:" << i << std::endl;}
168 };
169 struct B {
170 A *m_a;
171 B(){static A s_a(10);m_a=&s_a;std::cout << "CTOR B" << std::endl;}
172 ~B(){std::cout << "DTOR B:" << (*m_a).i << std::endl;(*m_a).i = 20;}
173 };
174 int main(void) {struct B b;return 0;}
175 EOF
176 atf_check -s exit:0 -o ignore -e ignore c++ -static -o hello test.cpp
177 atf_check -s exit:0 -o inline:"CTOR A\nCTOR B\nDTOR B:10\nDTOR A:20\n" ./hello
178 }
179
180 static_destructor_pic_body() {
181 cat > test.cpp << EOF
182 #include <cstdlib>
183 int callpic(void);
184 int main(void) {callpic();exit(0);}
185 EOF
186 cat > pic.cpp << EOF
187 #include <iostream>
188 struct A {
189 int i;
190 A(int i):i(i){std::cout << "CTOR A" << std::endl;}
191 ~A() {std::cout << "DTOR A:" << i << std::endl;}
192 };
193 struct B {
194 A *m_a;
195 B(){static A s_a(10);m_a=&s_a;std::cout << "CTOR B" << std::endl;}
196 ~B(){std::cout << "DTOR B:" << (*m_a).i << std::endl;(*m_a).i = 20;}
197 };
198 int callpic(void) {struct B b;}
199 EOF
200
201 atf_check -s exit:0 -o ignore -e ignore \
202 c++ -fPIC -shared -o libtest.so pic.cpp
203 atf_check -s exit:0 -o ignore -e ignore \
204 c++ -o hello test.cpp -L. -ltest
205
206 export LD_LIBRARY_PATH=.
207 atf_check -s exit:0 -o inline:"CTOR A\nCTOR B\nDTOR B:10\nDTOR A:20\n" ./hello
208 }
209
210 static_destructor_pic_32_body() {
211 # check whether this arch is 64bit
212 if ! c++ -dM -E - < /dev/null | fgrep -q _LP64; then
213 atf_skip "this is not a 64 bit architecture"
214 fi
215 if ! c++ -m32 -dM -E - < /dev/null 2>/dev/null > ./def32; then
216 atf_skip "c++ -m32 not supported on this architecture"
217 else
218 if fgrep -q _LP64 ./def32; then
219 atf_fail "c++ -m32 does not generate netbsd32 binaries"
220 fi
221 fi
222
223 cat > test.cpp << EOF
224 #include <cstdlib>
225 int callpic(void);
226 int main(void) {callpic();exit(0);}
227 EOF
228 cat > pic.cpp << EOF
229 #include <iostream>
230 struct A {
231 int i;
232 A(int i):i(i){std::cout << "CTOR A" << std::endl;}
233 ~A() {std::cout << "DTOR A:" << i << std::endl;}
234 };
235 struct B {
236 A *m_a;
237 B(){static A s_a(10);m_a=&s_a;std::cout << "CTOR B" << std::endl;}
238 ~B(){std::cout << "DTOR B:" << (*m_a).i << std::endl;(*m_a).i = 20;}
239 };
240 int callpic(void) {struct B b;}
241 EOF
242
243 atf_check -s exit:0 -o ignore -e ignore \
244 c++ -m32 -fPIC -shared -o libtest.so pic.cpp
245 atf_check -s exit:0 -o ignore -e ignore \
246 c++ -m32 -o hello test.cpp -L. -ltest
247
248 export LD_LIBRARY_PATH=.
249 atf_check -s exit:0 -o inline:"CTOR A\nCTOR B\nDTOR B:10\nDTOR A:20\n" ./hello
250 }
251
252 static_destructor_pic_profile_body() {
253 cat > test.cpp << EOF
254 #include <cstdlib>
255 int callpic(void);
256 int main(void) {callpic();exit(0);}
257 EOF
258 cat > pic.cpp << EOF
259 #include <iostream>
260 struct A {
261 int i;
262 A(int i):i(i){std::cout << "CTOR A" << std::endl;}
263 ~A() {std::cout << "DTOR A:" << i << std::endl;}
264 };
265 struct B {
266 A *m_a;
267 B(){static A s_a(10);m_a=&s_a;std::cout << "CTOR B" << std::endl;}
268 ~B(){std::cout << "DTOR B:" << (*m_a).i << std::endl;(*m_a).i = 20;}
269 };
270 int callpic(void) {struct B b;}
271 EOF
272
273 atf_check -s exit:0 -o ignore -e ignore \
274 c++ -pg -fPIC -shared -o libtest.so pic.cpp
275 atf_check -s exit:0 -o ignore -e ignore \
276 c++ -pg -o hello test.cpp -L. -ltest
277
278 export LD_LIBRARY_PATH=.
279 atf_check -s exit:0 -o inline:"CTOR A\nCTOR B\nDTOR B:10\nDTOR A:20\n" ./hello
280 }
281
282 static_destructor_pic_profile_32_body() {
283 # check whether this arch is 64bit
284 if ! c++ -dM -E - < /dev/null | fgrep -q _LP64; then
285 atf_skip "this is not a 64 bit architecture"
286 fi
287 if ! c++ -m32 -dM -E - < /dev/null 2>/dev/null > ./def32; then
288 atf_skip "c++ -m32 not supported on this architecture"
289 else
290 if fgrep -q _LP64 ./def32; then
291 atf_fail "c++ -m32 does not generate netbsd32 binaries"
292 fi
293 fi
294
295 cat > test.cpp << EOF
296 #include <cstdlib>
297 int callpic(void);
298 int main(void) {callpic();exit(0);}
299 EOF
300 cat > pic.cpp << EOF
301 #include <iostream>
302 struct A {
303 int i;
304 A(int i):i(i){std::cout << "CTOR A" << std::endl;}
305 ~A() {std::cout << "DTOR A:" << i << std::endl;}
306 };
307 struct B {
308 A *m_a;
309 B(){static A s_a(10);m_a=&s_a;std::cout << "CTOR B" << std::endl;}
310 ~B(){std::cout << "DTOR B:" << (*m_a).i << std::endl;(*m_a).i = 20;}
311 };
312 int callpic(void) {struct B b;}
313 EOF
314
315 atf_check -s exit:0 -o ignore -e ignore \
316 c++ -m32 -pg -fPIC -shared -o libtest.so pic.cpp
317 atf_check -s exit:0 -o ignore -e ignore \
318 c++ -m32 -pg -o hello test.cpp -L. -ltest
319
320 export LD_LIBRARY_PATH=.
321 atf_check -s exit:0 -o inline:"CTOR A\nCTOR B\nDTOR B:10\nDTOR A:20\n" ./hello
322 }
323
324 static_destructor_pie_body() {
325 # check whether this arch supports -pie
326 if ! c++ -pie -dM -E - < /dev/null 2>/dev/null >/dev/null; then
327 atf_skip "c++ -pie not supported on this architecture"
328 fi
329 cat > test.cpp << EOF
330 #include <iostream>
331 struct A {
332 int i;
333 A(int i):i(i){std::cout << "CTOR A" << std::endl;}
334 ~A() {std::cout << "DTOR A:" << i << std::endl;}
335 };
336 struct B {
337 A *m_a;
338 B(){static A s_a(10);m_a=&s_a;std::cout << "CTOR B" << std::endl;}
339 ~B(){std::cout << "DTOR B:" << (*m_a).i << std::endl;(*m_a).i = 20;}
340 };
341 int main(void) {struct B b;return 0;}
342 EOF
343 atf_check -s exit:0 -o ignore -e ignore c++ -fpie -pie -o hello test.cpp
344 atf_check -s exit:0 -o inline:"CTOR A\nCTOR B\nDTOR B:10\nDTOR A:20\n" ./hello
345 }
346
347 static_destructor32_body() {
348 # check whether this arch is 64bit
349 if ! c++ -dM -E - < /dev/null | fgrep -q _LP64; then
350 atf_skip "this is not a 64 bit architecture"
351 fi
352 if ! c++ -m32 -dM -E - < /dev/null 2>/dev/null > ./def32; then
353 atf_skip "c++ -m32 not supported on this architecture"
354 else
355 if fgrep -q _LP64 ./def32; then
356 atf_fail "c++ -m32 does not generate netbsd32 binaries"
357 fi
358 fi
359
360 cat > test.cpp << EOF
361 #include <iostream>
362 struct A {
363 int i;
364 A(int i):i(i){std::cout << "CTOR A" << std::endl;}
365 ~A() {std::cout << "DTOR A:" << i << std::endl;}
366 };
367 struct B {
368 A *m_a;
369 B(){static A s_a(10);m_a=&s_a;std::cout << "CTOR B" << std::endl;}
370 ~B(){std::cout << "DTOR B:" << (*m_a).i << std::endl;(*m_a).i = 20;}
371 };
372 int main(void) {struct B b;return 0;}
373 EOF
374 atf_check -s exit:0 -o ignore -e ignore c++ -o hello32 -m32 test.cpp
375 atf_check -s exit:0 -o ignore -e ignore c++ -o hello64 test.cpp
376 file -b ./hello32 > ./ftype32
377 file -b ./hello64 > ./ftype64
378 if diff ./ftype32 ./ftype64 >/dev/null; then
379 atf_fail "generated binaries do not differ"
380 fi
381 echo "32bit binaries on this platform are:"
382 cat ./ftype32
383 echo "While native (64bit) binaries are:"
384 cat ./ftype64
385 atf_check -s exit:0 -o inline:"CTOR A\nCTOR B\nDTOR B:10\nDTOR A:20\n" ./hello32
386
387 # do another test with static 32bit binaries
388 cat > test.cpp << EOF
389 #include <iostream>
390 struct A {
391 int i;
392 A(int i):i(i){std::cout << "CTOR A" << std::endl;}
393 ~A() {std::cout << "DTOR A:" << i << std::endl;}
394 };
395 struct B {
396 A *m_a;
397 B(){static A s_a(10);m_a=&s_a;std::cout << "CTOR B" << std::endl;}
398 ~B(){std::cout << "DTOR B:" << (*m_a).i << std::endl;(*m_a).i = 20;}
399 };
400 int main(void) {struct B b;return 0;}
401 EOF
402 atf_check -s exit:0 -o ignore -e ignore c++ -o hello -m32 \
403 -static test.cpp
404 atf_check -s exit:0 -o inline:"CTOR A\nCTOR B\nDTOR B:10\nDTOR A:20\n" ./hello
405 }
406
407 atf_init_test_cases()
408 {
409
410 atf_add_test_case static_destructor
411 atf_add_test_case static_destructor_profile
412 atf_add_test_case static_destructor_pic
413 atf_add_test_case static_destructor_pie
414 atf_add_test_case static_destructor32
415 atf_add_test_case static_destructor_static
416 atf_add_test_case static_destructor_pic_32
417 atf_add_test_case static_destructor_pic_profile
418 atf_add_test_case static_destructor_pic_profile_32
419 atf_add_test_case static_destructor_profile_32
420 }
421