HPCToolkit
wrapper-macros.h
Go to the documentation of this file.
1 #ifndef _WRAPPER_MACROS_H_
2 #define _WRAPPER_MACROS_H_
3 //*****************************************************************************
4 // File:
5 // wrapper-macros.h
6 //
7 // Purpose:
8 // use C99 variadic macros to count and cast a list of macro arguments
9 //
10 // Modification History
11 //
12 // 2010/12/27 - created Bill Scherer and John Mellor-Crummey
13 //
14 //*****************************************************************************
15 
16 
17 //*****************************************************************************
18 // VA_DECLARE_ARGSXX:
19 // a set of macros to construct an argument list by pasting together type and
20 // variable pairs
21 //*****************************************************************************
22 #define VA_DECLARE_ARG(type_t, x) type_t x
23 
24 #define VA_DECLARE_ARGS20(type_t, x, ...) \
25  VA_DECLARE_ARG(type_t, x), VA_DECLARE_ARGS18(__VA_ARGS__)
26 
27 #define VA_DECLARE_ARGS18(type_t, x, ...) \
28  VA_DECLARE_ARG(type_t, x), VA_DECLARE_ARGS16(__VA_ARGS__)
29 
30 #define VA_DECLARE_ARGS16(type_t, x, ...) \
31  VA_DECLARE_ARG(type_t, x), VA_DECLARE_ARGS14(__VA_ARGS__)
32 
33 #define VA_DECLARE_ARGS14(type_t, x, ...) \
34  VA_DECLARE_ARG(type_t, x), VA_DECLARE_ARGS12(__VA_ARGS__)
35 
36 #define VA_DECLARE_ARGS12(type_t, x, ...) \
37  VA_DECLARE_ARG(type_t, x), VA_DECLARE_ARGS10(__VA_ARGS__)
38 
39 #define VA_DECLARE_ARGS10(type_t, x, ...) \
40  VA_DECLARE_ARG(type_t, x), VA_DECLARE_ARGS8(__VA_ARGS__)
41 
42 #define VA_DECLARE_ARGS8(type_t, x, ...) \
43  VA_DECLARE_ARG(type_t, x), VA_DECLARE_ARGS6(__VA_ARGS__)
44 
45 #define VA_DECLARE_ARGS6(type_t, x, ...) \
46  VA_DECLARE_ARG(type_t, x), VA_DECLARE_ARGS4(__VA_ARGS__)
47 
48 #define VA_DECLARE_ARGS4(type_t, x, ...) \
49  VA_DECLARE_ARG(type_t, x), VA_DECLARE_ARGS2(__VA_ARGS__)
50 
51 #define VA_DECLARE_ARGS2(type_t, x, ...) \
52  VA_DECLARE_ARG(type_t, x)
53 
54 #define VA_DECLARE_ARGS1(type_t, ...) type_t
55 
56 #define VA_DECLARE_ARGS0(...) void
57 
58 
59 //*****************************************************************************
60 // VA_CALL_ARGSXX:
61 // a set of macros to cast each of a sequence of arguments in a __VA_ARGS__
62 // list to type_t
63 //*****************************************************************************
64 #define VA_CALL_ARG(type_t, x) x
65 
66 #define VA_CALL_ARGS20(type_t, x, ...) \
67  VA_CALL_ARG(type_t, x), VA_CALL_ARGS18(__VA_ARGS__)
68 
69 #define VA_CALL_ARGS18(type_t, x, ...) \
70  VA_CALL_ARG(type_t, x), VA_CALL_ARGS16(__VA_ARGS__)
71 
72 #define VA_CALL_ARGS16(type_t, x, ...) \
73  VA_CALL_ARG(type_t, x), VA_CALL_ARGS14(__VA_ARGS__)
74 
75 #define VA_CALL_ARGS14(type_t, x, ...) \
76  VA_CALL_ARG(type_t, x), VA_CALL_ARGS12(__VA_ARGS__)
77 
78 #define VA_CALL_ARGS12(type_t, x, ...) \
79  VA_CALL_ARG(type_t, x), VA_CALL_ARGS10(__VA_ARGS__)
80 
81 #define VA_CALL_ARGS10(type_t, x, ...) \
82  VA_CALL_ARG(type_t, x), VA_CALL_ARGS8(__VA_ARGS__)
83 
84 #define VA_CALL_ARGS8(type_t, x, ...) \
85  VA_CALL_ARG(type_t, x), VA_CALL_ARGS6(__VA_ARGS__)
86 
87 #define VA_CALL_ARGS6(type_t, x, ...) \
88  VA_CALL_ARG(type_t, x), VA_CALL_ARGS4(__VA_ARGS__)
89 
90 #define VA_CALL_ARGS4(type_t, x, ...) \
91  VA_CALL_ARG(type_t, x), VA_CALL_ARGS2(__VA_ARGS__)
92 
93 #define VA_CALL_ARGS2(type_t, x, ...) \
94  VA_CALL_ARG(type_t, x)
95 
96 #define VA_CALL_ARGS1(type_t, ...)
97 
98 #define VA_CALL_ARGS0(...)
99 
100 //*****************************************************************************
101 // VA_COMMA0, VA_COMMA1:
102 // macros that expand to the number of commas indicated by their suffix.
103 //*****************************************************************************
104 #define VA_COMMA0
105 #define VA_COMMA1 ,
106 
107 
108 //*****************************************************************************
109 // _VA_CONCAT2:
110 // macro to concatenate a pair of arguments into a name.
111 //*****************************************************************************
112 #define _VA_CONCAT2(name,x) name##x
113 
114 
115 //*****************************************************************************
116 // _VA_CONCAT3:
117 // macro to concatenate a pair of arguments into a name.
118 //*****************************************************************************
119 #define _VA_CONCAT3(x,y,z,...) x##y##z
120 
121 
122 //*****************************************************************************
123 // __twentyone_and_0__:
124 // helper macro that expands to twentyone placeholder arguments followed
125 // by a 0.
126 //*****************************************************************************
127 #define __twentyone_and_0__ \
128  0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 0
129 
130 
131 //*****************************************************************************
132 // _VA_SELECT22:
133 // _VA_SELECT22_INTERNAL:
134 // pair of macros to expand to 22nd argument. VA_SELECT22 macro ensures
135 // that argument list is completely expanded before calling
136 // _VA_SELECT22_INTERNAL
137 //*****************************************************************************
138 #define _VA_SELECT22_INTERNAL(_0,_1,_2,_3,_4,_5,_6,_7, \
139  _8,_9,_10,_11,_12,_13,_14,_15,_16,_17,_18,_19,_20,_21,...) _21
140 
141 #define _VA_SELECT22(...) _VA_SELECT22_INTERNAL(__VA_ARGS__)
142 
143 
144 //*****************************************************************************
145 // VA_COUNT_ARGS: macro that expands to the number of arguments
146 // WARNING: will give unpredictable results if more than 16 arguments supplied.
147 //*****************************************************************************
148 #define VA_COUNT_ARGS(...) \
149  _VA_SELECT22(_VA_CONCAT3(__twentyone,_and_0__,__VA_ARGS__), \
150  __VA_ARGS__,20,19,18,17,16,15,14,13,12,11,10,9,8,7,6,5,4,3,2,1)
151 
152 
153 #define X_ARGS(...) \
154  _VA_CONCAT3(__twentyone,_and_0__,__VA_ARGS__)
155 //*****************************************************************************
156 // ONE_IF_EMPTY: expand to a 1 if a non-zero number of arguments are supplied.
157 // WARNING: will give unpredictable results if more than 16 arguments supplied.
158 //*****************************************************************************
159 #define ONE_IF_NONEMPTY(...) \
160  _VA_SELECT22(_VA_CONCAT3(__twentyone,_and_0__,__VA_ARGS__), \
161  __VA_ARGS__,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1)
162 
163 
164 //*****************************************************************************
165 // VA_CONCAT_EVAL:
166 // macro to join two parts of a macro name and evaluate the result.
167 //*****************************************************************************
168 #define VA_CONCAT2_EVAL(name,x) _VA_CONCAT2(name,x)
169 
170 
171 //*****************************************************************************
172 // VA_COMMA_IF_NONEMPTY:
173 // macro that expands to a comma if the argument list is not empty.
174 //*****************************************************************************
175 #define VA_COMMA_IF_NONEMPTY(...) \
176  VA_CONCAT2_EVAL(VA_COMMA,ONE_IF_NONEMPTY(__VA_ARGS__))
177 
178 
179 //*****************************************************************************
180 // VA_DECLARE_ARGS:
181 // assembles a function declaration argument list with type variable pairs
182 //*****************************************************************************
183 #define VA_DECLARE_ARGS(...) \
184  VA_CONCAT2_EVAL(VA_DECLARE_ARGS,VA_COUNT_ARGS(__VA_ARGS__))( \
185  __VA_ARGS__)
186 
187 
188 //*****************************************************************************
189 // VA_CALL_ARGS:
190 // assembles a function argument list containing just a list of variables
191 //*****************************************************************************
192 #define VA_CALL_ARGS(...) \
193  VA_CONCAT2_EVAL(VA_CALL_ARGS,VA_COUNT_ARGS(__VA_ARGS__))( \
194  __VA_ARGS__)
195 
196 #define VA_FN_CALL(fn, ...) \
197  fn(VA_CONCAT2_EVAL(VA_CALL_ARGS,VA_COUNT_ARGS(__VA_ARGS__))( \
198  __VA_ARGS__))
199 
200 
201 #define VA_FN_DECLARE(tfn, fn, ...) \
202  tfn fn(VA_CONCAT2_EVAL(VA_DECLARE_ARGS,VA_COUNT_ARGS(__VA_ARGS__))( \
203  __VA_ARGS__))
204 
205 
206 // Test cases: anytime you change these macros, make sure these tests pass.
207 
208 #if 0
209 VA_FN_CALL( Fun)
210 VA_FN_CALL( Fun, t1, 1)
211 VA_FN_CALL( Fun, t1, 1, t2, 2)
212 VA_FN_CALL( Fun, t1, 1, t2, 2, t3, 3)
213 VA_FN_CALL( Fun, t1, 1, t2, 2, t3, 3, t4, 4)
214 VA_FN_CALL( Fun, t1, 1, t2, 2, t3, 3, t4, 4, t5, 5)
215 VA_FN_CALL( Fun, t1, 1, t2, 2, t3, 3, t4, 4, t5, 5, t6, 6)
216 VA_FN_CALL( Fun, t1, 1, t2, 2, t3, 3, t4, 4, t5, 5, t6, 6, t7, 7)
217 VA_FN_CALL( Fun, t1, 1, t2, 2, t3, 3, t4, 4, t5, 5, t6, 6, t7, 7, t8, 8)
218 VA_FN_CALL( Fun, t1, 1, t2, 2, t3, 3, t4, 4, t5, 5, t6, 6, t7, 7, t8, 8 , t9, 9)
219 VA_FN_CALL( Fun, t1, 1, t2, 2, t3, 3, t4, 4, t5, 5, t6, 6, t7, 7, t8, 8 , t9, 9, t10 *, 10)
220 
221 VA_FN_DECLARE(ret, Fun)
222 VA_FN_DECLARE(ret, Fun, void)
223 VA_FN_DECLARE(ret, Fun, t1, 1)
224 VA_FN_DECLARE(ret, Fun, t1, 1, t2, 2)
225 VA_FN_DECLARE(ret, Fun, t1, 1, t2, 2, t3, 3)
226 VA_FN_DECLARE(ret, Fun, t1, 1, t2, 2, t3, 3, t4, 4)
227 VA_FN_DECLARE(ret, Fun, t1, 1, t2, 2, t3, 3, t4, 4, t5, 5)
228 VA_FN_DECLARE(ret, Fun, t1, 1, t2, 2, t3, 3, t4, 4, t5, 5, t6, 6)
229 VA_FN_DECLARE(ret, Fun, t1, 1, t2, 2, t3, 3, t4, 4, t5, 5, t6, 6, t7, 7)
230 VA_FN_DECLARE(ret, Fun, t1, 1, t2, 2, t3, 3, t4, 4, t5, 5, t6, 6, t7, 7, t8, 8)
231 VA_FN_DECLARE(ret, Fun, t1, 1, t2, 2, t3, 3, t4, 4, t5, 5, t6, 6, t7, 7, t8, 8 , t9, 9)
232 VA_FN_DECLARE(ret, Fun, t1, 1, t2, 2, t3, 3, t4, 4, t5, 5, t6, 6, t7, 7, t8, 8 , t9, 9, t10 *, 10)
233 #endif
234 
235 #endif
#define VA_FN_CALL(fn,...)
#define VA_FN_DECLARE(tfn, fn,...)