gdb: Initial baremetal riscv support
[deliverable/binutils-gdb.git] / gdb / testsuite / gdb.base / infcall-nested-structs.c
CommitLineData
dbbb1059
AB
1/* This testcase is part of GDB, the GNU debugger.
2
3 Copyright 2018 Free Software Foundation, Inc.
4
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; either version 3 of the License, or
8 (at your option) any later version.
9
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
14
15 You should have received a copy of the GNU General Public License
16 along with this program. If not, see <http://www.gnu.org/licenses/>. */
17
18/* This file is used for testing GDBs ability to pass structures to, and
19 return structures from, functions. All of the structures in this test
20 are special in that they are small structures containing only 1 or 2
21 scalar fields, the fields can be inside nested structures, and there can
22 be empty structures around too.
23
24 This test was originally written for RiscV which has some special ABI
25 rules for structures like these, however, there should be no harm in
26 running these tests on other targets, though in many cases the
27 structures will treated no differently to the structures already covered
28 in the structs.exp test script. */
29
30#include <string.h>
31
32/* Useful abreviations. */
33typedef char tc;
34typedef short ts;
35typedef int ti;
36typedef long tl;
37typedef long long tll;
38typedef float tf;
39typedef double td;
40typedef long double tld;
41
42#ifdef TEST_COMPLEX
43typedef float _Complex tfc;
44typedef double _Complex tdc;
45typedef long double _Complex tldc;
46#endif /* TEST_COMPLEX */
47
48#define MAKE_CHECK_FUNCS(TYPE) \
49 int \
50 check_arg_ ## TYPE (struct TYPE arg) \
51 { \
52 return cmp_ ## TYPE (arg, ref_val_ ## TYPE); \
53 } \
54 \
55 struct TYPE \
56 rtn_str_ ## TYPE (void) \
57 { \
58 return (ref_val_ ## TYPE); \
59 }
60
61#define REF_VAL(NAME) struct NAME ref_val_ ## NAME
62#define ES(NAME) struct { } NAME
63
64#if defined tA && ! defined tB
65
66/* Structures with a single field nested to various depths, along with
67 some empty structures. */
68struct struct01 { ES(es1); struct { struct { tA a; } s1; } s2; };
69struct struct02 { tA a; struct { struct { ES(es1); } s1; } s2; };
70struct struct03 { struct { struct { ES(es1); } s1; } s2; ES(es1); struct { struct { tA a; } s3; } s4;};
71struct struct04 { ES(es1); ES(es2); tA a; ES(es3); };
72
73int cmp_struct01 (struct struct01 a, struct struct01 b)
74{ return a.s2.s1.a == b.s2.s1.a; }
75
76int cmp_struct02 (struct struct02 a, struct struct02 b)
77{ return a.a == b.a; }
78
79int cmp_struct03 (struct struct03 a, struct struct03 b)
80{ return a.s4.s3.a == b.s4.s3.a; }
81
82int cmp_struct04 (struct struct04 a, struct struct04 b)
83{ return a.a == b.a; }
84
85REF_VAL(struct01) = { {}, { { 'a' } } };
86REF_VAL(struct02) = { 'a', { { {} } } };
87REF_VAL(struct03) = { { { {} } }, {}, { { 'a' } } };
88REF_VAL(struct04) = { {}, {}, 'a', {} };
89
90#elif defined tA && defined tB
91
92/* These structures all have 2 fields, nested to various depths, along
93 with some empty structures. */
94struct struct01 { struct { tA a; } s1; ES (e1); struct { struct { tB b; } s2;} s3;};
95struct struct02 { struct { struct { tA a; } s1; ES(e1); } s2; struct { struct { tB b; } s3;} s4; ES(e2);};
96struct struct03 { ES(e1); tA a; ES (e2); struct { struct { tB b; } s2;} s3;};
97struct struct04 { ES(e1); ES (e2); struct { struct { struct { tA a; struct { ES(e3); } s1; tB b; } s2; } s3;} s4;};
98
99int cmp_struct01 (struct struct01 a, struct struct01 b)
100{ return a.s1.a == b.s1.a && a.s3.s2.b == b.s3.s2.b; }
101
102int cmp_struct02 (struct struct02 a, struct struct02 b)
103{ return a.s2.s1.a == b.s2.s1.a && a.s4.s3.b == b.s4.s3.b; }
104
105int cmp_struct03 (struct struct03 a, struct struct03 b)
106{ return a.a == b.a && a.s3.s2.b == b.s3.s2.b; }
107
108int cmp_struct04 (struct struct04 a, struct struct04 b)
109{ return a.s4.s3.s2.a == b.s4.s3.s2.a && a.s4.s3.s2.b == b.s4.s3.s2.b; }
110
111REF_VAL(struct01) = { { 'a' }, {}, { { '1' } } };
112REF_VAL(struct02) = { { { 'a' }, {} }, { { '1' } }, {} };
113REF_VAL(struct03) = { {}, 'a', {}, { { '1' } } };
114REF_VAL(struct04) = { {}, {}, { { { 'a', {}, '1'} } } } ;
115
116#else
117
118#error "Incorrect configuration of tA and tB defines"
119
120#endif
121
122/* Create all of the functions GDB will call to check functionality. */
123MAKE_CHECK_FUNCS(struct01)
124MAKE_CHECK_FUNCS(struct02)
125MAKE_CHECK_FUNCS(struct03)
126MAKE_CHECK_FUNCS(struct04)
127
128#define CALL_LINE(NAME) val += check_arg_ ## NAME (rtn_str_ ## NAME ())
129
130int
131call_all ()
132{
133 int val;
134
135 CALL_LINE(struct01);
136 CALL_LINE(struct02);
137 CALL_LINE(struct03);
138 CALL_LINE(struct04);
139
140 return (val != 4);
141}
142
143void
144breakpt (void)
145{
146 /* Nothing. */
147}
148
149int
150main ()
151{
152 int res;
153
154 res = call_all ();
155 breakpt (); /* Break Here. */
156 return res;
157}
This page took 0.041595 seconds and 4 git commands to generate.