File: | tools/polly/lib/External/isl/isl_ast.c |
Warning: | line 2403, column 2 Use of memory after it is freed |
Press '?' to see keyboard shortcuts
Keyboard shortcuts:
1 | /* | |||
2 | * Copyright 2012-2013 Ecole Normale Superieure | |||
3 | * | |||
4 | * Use of this software is governed by the MIT license | |||
5 | * | |||
6 | * Written by Sven Verdoolaege, | |||
7 | * Ecole Normale Superieure, 45 rue d’Ulm, 75230 Paris, France | |||
8 | */ | |||
9 | ||||
10 | #include <string.h> | |||
11 | ||||
12 | #include <isl/val.h> | |||
13 | #include <isl_ast_private.h> | |||
14 | ||||
15 | #undef BASEast_node | |||
16 | #define BASEast_node ast_expr | |||
17 | ||||
18 | #include <isl_list_templ.c> | |||
19 | ||||
20 | #undef BASEast_node | |||
21 | #define BASEast_node ast_node | |||
22 | ||||
23 | #include <isl_list_templ.c> | |||
24 | ||||
25 | isl_ctx *isl_ast_print_options_get_ctx( | |||
26 | __isl_keep isl_ast_print_options *options) | |||
27 | { | |||
28 | return options ? options->ctx : NULL((void*)0); | |||
29 | } | |||
30 | ||||
31 | __isl_give isl_ast_print_options *isl_ast_print_options_alloc(isl_ctx *ctx) | |||
32 | { | |||
33 | isl_ast_print_options *options; | |||
34 | ||||
35 | options = isl_calloc_type(ctx, isl_ast_print_options)((isl_ast_print_options *)isl_calloc_or_die(ctx, 1, sizeof(isl_ast_print_options ))); | |||
36 | if (!options) | |||
37 | return NULL((void*)0); | |||
38 | ||||
39 | options->ctx = ctx; | |||
40 | isl_ctx_ref(ctx); | |||
41 | options->ref = 1; | |||
42 | ||||
43 | return options; | |||
44 | } | |||
45 | ||||
46 | __isl_give isl_ast_print_options *isl_ast_print_options_dup( | |||
47 | __isl_keep isl_ast_print_options *options) | |||
48 | { | |||
49 | isl_ctx *ctx; | |||
50 | isl_ast_print_options *dup; | |||
51 | ||||
52 | if (!options) | |||
53 | return NULL((void*)0); | |||
54 | ||||
55 | ctx = isl_ast_print_options_get_ctx(options); | |||
56 | dup = isl_ast_print_options_alloc(ctx); | |||
57 | if (!dup) | |||
58 | return NULL((void*)0); | |||
59 | ||||
60 | dup->print_for = options->print_for; | |||
61 | dup->print_for_user = options->print_for_user; | |||
62 | dup->print_user = options->print_user; | |||
63 | dup->print_user_user = options->print_user_user; | |||
64 | ||||
65 | return dup; | |||
66 | } | |||
67 | ||||
68 | __isl_give isl_ast_print_options *isl_ast_print_options_cow( | |||
69 | __isl_take isl_ast_print_options *options) | |||
70 | { | |||
71 | if (!options) | |||
72 | return NULL((void*)0); | |||
73 | ||||
74 | if (options->ref == 1) | |||
75 | return options; | |||
76 | options->ref--; | |||
77 | return isl_ast_print_options_dup(options); | |||
78 | } | |||
79 | ||||
80 | __isl_give isl_ast_print_options *isl_ast_print_options_copy( | |||
81 | __isl_keep isl_ast_print_options *options) | |||
82 | { | |||
83 | if (!options) | |||
84 | return NULL((void*)0); | |||
85 | ||||
86 | options->ref++; | |||
87 | return options; | |||
88 | } | |||
89 | ||||
90 | __isl_null isl_ast_print_options *isl_ast_print_options_free( | |||
91 | __isl_take isl_ast_print_options *options) | |||
92 | { | |||
93 | if (!options) | |||
94 | return NULL((void*)0); | |||
95 | ||||
96 | if (--options->ref > 0) | |||
97 | return NULL((void*)0); | |||
98 | ||||
99 | isl_ctx_deref(options->ctx); | |||
100 | ||||
101 | free(options); | |||
102 | return NULL((void*)0); | |||
103 | } | |||
104 | ||||
105 | /* Set the print_user callback of "options" to "print_user". | |||
106 | * | |||
107 | * If this callback is set, then it used to print user nodes in the AST. | |||
108 | * Otherwise, the expression associated to the user node is printed. | |||
109 | */ | |||
110 | __isl_give isl_ast_print_options *isl_ast_print_options_set_print_user( | |||
111 | __isl_take isl_ast_print_options *options, | |||
112 | __isl_give isl_printer *(*print_user)(__isl_take isl_printer *p, | |||
113 | __isl_take isl_ast_print_options *options, | |||
114 | __isl_keep isl_ast_node *node, void *user), | |||
115 | void *user) | |||
116 | { | |||
117 | options = isl_ast_print_options_cow(options); | |||
118 | if (!options) | |||
119 | return NULL((void*)0); | |||
120 | ||||
121 | options->print_user = print_user; | |||
122 | options->print_user_user = user; | |||
123 | ||||
124 | return options; | |||
125 | } | |||
126 | ||||
127 | /* Set the print_for callback of "options" to "print_for". | |||
128 | * | |||
129 | * If this callback is set, then it used to print for nodes in the AST. | |||
130 | */ | |||
131 | __isl_give isl_ast_print_options *isl_ast_print_options_set_print_for( | |||
132 | __isl_take isl_ast_print_options *options, | |||
133 | __isl_give isl_printer *(*print_for)(__isl_take isl_printer *p, | |||
134 | __isl_take isl_ast_print_options *options, | |||
135 | __isl_keep isl_ast_node *node, void *user), | |||
136 | void *user) | |||
137 | { | |||
138 | options = isl_ast_print_options_cow(options); | |||
139 | if (!options) | |||
140 | return NULL((void*)0); | |||
141 | ||||
142 | options->print_for = print_for; | |||
143 | options->print_for_user = user; | |||
144 | ||||
145 | return options; | |||
146 | } | |||
147 | ||||
148 | __isl_give isl_ast_expr *isl_ast_expr_copy(__isl_keep isl_ast_expr *expr) | |||
149 | { | |||
150 | if (!expr) | |||
151 | return NULL((void*)0); | |||
152 | ||||
153 | expr->ref++; | |||
154 | return expr; | |||
155 | } | |||
156 | ||||
157 | __isl_give isl_ast_expr *isl_ast_expr_dup(__isl_keep isl_ast_expr *expr) | |||
158 | { | |||
159 | int i; | |||
160 | isl_ctx *ctx; | |||
161 | isl_ast_expr *dup; | |||
162 | ||||
163 | if (!expr) | |||
164 | return NULL((void*)0); | |||
165 | ||||
166 | ctx = isl_ast_expr_get_ctx(expr); | |||
167 | switch (expr->type) { | |||
168 | case isl_ast_expr_int: | |||
169 | dup = isl_ast_expr_from_val(isl_val_copy(expr->u.v)); | |||
170 | break; | |||
171 | case isl_ast_expr_id: | |||
172 | dup = isl_ast_expr_from_id(isl_id_copy(expr->u.id)); | |||
173 | break; | |||
174 | case isl_ast_expr_op: | |||
175 | dup = isl_ast_expr_alloc_op(ctx, | |||
176 | expr->u.op.op, expr->u.op.n_arg); | |||
177 | if (!dup) | |||
178 | return NULL((void*)0); | |||
179 | for (i = 0; i < expr->u.op.n_arg; ++i) | |||
180 | dup->u.op.args[i] = | |||
181 | isl_ast_expr_copy(expr->u.op.args[i]); | |||
182 | break; | |||
183 | case isl_ast_expr_error: | |||
184 | dup = NULL((void*)0); | |||
185 | } | |||
186 | ||||
187 | if (!dup) | |||
188 | return NULL((void*)0); | |||
189 | ||||
190 | return dup; | |||
191 | } | |||
192 | ||||
193 | __isl_give isl_ast_expr *isl_ast_expr_cow(__isl_take isl_ast_expr *expr) | |||
194 | { | |||
195 | if (!expr) | |||
196 | return NULL((void*)0); | |||
197 | ||||
198 | if (expr->ref == 1) | |||
199 | return expr; | |||
200 | expr->ref--; | |||
201 | return isl_ast_expr_dup(expr); | |||
202 | } | |||
203 | ||||
204 | __isl_null isl_ast_expr *isl_ast_expr_free(__isl_take isl_ast_expr *expr) | |||
205 | { | |||
206 | int i; | |||
207 | ||||
208 | if (!expr) | |||
209 | return NULL((void*)0); | |||
210 | ||||
211 | if (--expr->ref > 0) | |||
212 | return NULL((void*)0); | |||
213 | ||||
214 | isl_ctx_deref(expr->ctx); | |||
215 | ||||
216 | switch (expr->type) { | |||
217 | case isl_ast_expr_int: | |||
218 | isl_val_free(expr->u.v); | |||
219 | break; | |||
220 | case isl_ast_expr_id: | |||
221 | isl_id_free(expr->u.id); | |||
222 | break; | |||
223 | case isl_ast_expr_op: | |||
224 | if (expr->u.op.args) | |||
225 | for (i = 0; i < expr->u.op.n_arg; ++i) | |||
226 | isl_ast_expr_free(expr->u.op.args[i]); | |||
227 | free(expr->u.op.args); | |||
228 | break; | |||
229 | case isl_ast_expr_error: | |||
230 | break; | |||
231 | } | |||
232 | ||||
233 | free(expr); | |||
234 | return NULL((void*)0); | |||
235 | } | |||
236 | ||||
237 | isl_ctx *isl_ast_expr_get_ctx(__isl_keep isl_ast_expr *expr) | |||
238 | { | |||
239 | return expr ? expr->ctx : NULL((void*)0); | |||
240 | } | |||
241 | ||||
242 | enum isl_ast_expr_type isl_ast_expr_get_type(__isl_keep isl_ast_expr *expr) | |||
243 | { | |||
244 | return expr ? expr->type : isl_ast_expr_error; | |||
245 | } | |||
246 | ||||
247 | /* Return the integer value represented by "expr". | |||
248 | */ | |||
249 | __isl_give isl_val *isl_ast_expr_get_val(__isl_keep isl_ast_expr *expr) | |||
250 | { | |||
251 | if (!expr) | |||
252 | return NULL((void*)0); | |||
253 | if (expr->type != isl_ast_expr_int) | |||
254 | isl_die(isl_ast_expr_get_ctx(expr), isl_error_invalid,do { isl_handle_error(isl_ast_expr_get_ctx(expr), isl_error_invalid , "expression not an int", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 255); return ((void*)0); } while (0) | |||
255 | "expression not an int", return NULL)do { isl_handle_error(isl_ast_expr_get_ctx(expr), isl_error_invalid , "expression not an int", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 255); return ((void*)0); } while (0); | |||
256 | return isl_val_copy(expr->u.v); | |||
257 | } | |||
258 | ||||
259 | __isl_give isl_id *isl_ast_expr_get_id(__isl_keep isl_ast_expr *expr) | |||
260 | { | |||
261 | if (!expr) | |||
262 | return NULL((void*)0); | |||
263 | if (expr->type != isl_ast_expr_id) | |||
264 | isl_die(isl_ast_expr_get_ctx(expr), isl_error_invalid,do { isl_handle_error(isl_ast_expr_get_ctx(expr), isl_error_invalid , "expression not an identifier", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 265); return ((void*)0); } while (0) | |||
265 | "expression not an identifier", return NULL)do { isl_handle_error(isl_ast_expr_get_ctx(expr), isl_error_invalid , "expression not an identifier", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 265); return ((void*)0); } while (0); | |||
266 | ||||
267 | return isl_id_copy(expr->u.id); | |||
268 | } | |||
269 | ||||
270 | enum isl_ast_op_type isl_ast_expr_get_op_type(__isl_keep isl_ast_expr *expr) | |||
271 | { | |||
272 | if (!expr) | |||
273 | return isl_ast_op_error; | |||
274 | if (expr->type != isl_ast_expr_op) | |||
275 | isl_die(isl_ast_expr_get_ctx(expr), isl_error_invalid,do { isl_handle_error(isl_ast_expr_get_ctx(expr), isl_error_invalid , "expression not an operation", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 276); return isl_ast_op_error; } while (0) | |||
276 | "expression not an operation", return isl_ast_op_error)do { isl_handle_error(isl_ast_expr_get_ctx(expr), isl_error_invalid , "expression not an operation", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 276); return isl_ast_op_error; } while (0); | |||
277 | return expr->u.op.op; | |||
278 | } | |||
279 | ||||
280 | int isl_ast_expr_get_op_n_arg(__isl_keep isl_ast_expr *expr) | |||
281 | { | |||
282 | if (!expr) | |||
283 | return -1; | |||
284 | if (expr->type != isl_ast_expr_op) | |||
285 | isl_die(isl_ast_expr_get_ctx(expr), isl_error_invalid,do { isl_handle_error(isl_ast_expr_get_ctx(expr), isl_error_invalid , "expression not an operation", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 286); return -1; } while (0) | |||
286 | "expression not an operation", return -1)do { isl_handle_error(isl_ast_expr_get_ctx(expr), isl_error_invalid , "expression not an operation", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 286); return -1; } while (0); | |||
287 | return expr->u.op.n_arg; | |||
288 | } | |||
289 | ||||
290 | __isl_give isl_ast_expr *isl_ast_expr_get_op_arg(__isl_keep isl_ast_expr *expr, | |||
291 | int pos) | |||
292 | { | |||
293 | if (!expr) | |||
294 | return NULL((void*)0); | |||
295 | if (expr->type != isl_ast_expr_op) | |||
296 | isl_die(isl_ast_expr_get_ctx(expr), isl_error_invalid,do { isl_handle_error(isl_ast_expr_get_ctx(expr), isl_error_invalid , "expression not an operation", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 297); return ((void*)0); } while (0) | |||
297 | "expression not an operation", return NULL)do { isl_handle_error(isl_ast_expr_get_ctx(expr), isl_error_invalid , "expression not an operation", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 297); return ((void*)0); } while (0); | |||
298 | if (pos < 0 || pos >= expr->u.op.n_arg) | |||
299 | isl_die(isl_ast_expr_get_ctx(expr), isl_error_invalid,do { isl_handle_error(isl_ast_expr_get_ctx(expr), isl_error_invalid , "index out of bounds", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 300); return ((void*)0); } while (0) | |||
300 | "index out of bounds", return NULL)do { isl_handle_error(isl_ast_expr_get_ctx(expr), isl_error_invalid , "index out of bounds", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 300); return ((void*)0); } while (0); | |||
301 | ||||
302 | return isl_ast_expr_copy(expr->u.op.args[pos]); | |||
303 | } | |||
304 | ||||
305 | /* Replace the argument at position "pos" of "expr" by "arg". | |||
306 | */ | |||
307 | __isl_give isl_ast_expr *isl_ast_expr_set_op_arg(__isl_take isl_ast_expr *expr, | |||
308 | int pos, __isl_take isl_ast_expr *arg) | |||
309 | { | |||
310 | expr = isl_ast_expr_cow(expr); | |||
311 | if (!expr || !arg) | |||
312 | goto error; | |||
313 | if (expr->type != isl_ast_expr_op) | |||
314 | isl_die(isl_ast_expr_get_ctx(expr), isl_error_invalid,do { isl_handle_error(isl_ast_expr_get_ctx(expr), isl_error_invalid , "expression not an operation", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 315); goto error; } while (0) | |||
315 | "expression not an operation", goto error)do { isl_handle_error(isl_ast_expr_get_ctx(expr), isl_error_invalid , "expression not an operation", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 315); goto error; } while (0); | |||
316 | if (pos < 0 || pos >= expr->u.op.n_arg) | |||
317 | isl_die(isl_ast_expr_get_ctx(expr), isl_error_invalid,do { isl_handle_error(isl_ast_expr_get_ctx(expr), isl_error_invalid , "index out of bounds", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 318); goto error; } while (0) | |||
318 | "index out of bounds", goto error)do { isl_handle_error(isl_ast_expr_get_ctx(expr), isl_error_invalid , "index out of bounds", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 318); goto error; } while (0); | |||
319 | ||||
320 | isl_ast_expr_free(expr->u.op.args[pos]); | |||
321 | expr->u.op.args[pos] = arg; | |||
322 | ||||
323 | return expr; | |||
324 | error: | |||
325 | isl_ast_expr_free(arg); | |||
326 | return isl_ast_expr_free(expr); | |||
327 | } | |||
328 | ||||
329 | /* Is "expr1" equal to "expr2"? | |||
330 | */ | |||
331 | isl_bool isl_ast_expr_is_equal(__isl_keep isl_ast_expr *expr1, | |||
332 | __isl_keep isl_ast_expr *expr2) | |||
333 | { | |||
334 | int i; | |||
335 | ||||
336 | if (!expr1 || !expr2) | |||
337 | return isl_bool_error; | |||
338 | ||||
339 | if (expr1 == expr2) | |||
340 | return isl_bool_true; | |||
341 | if (expr1->type != expr2->type) | |||
342 | return isl_bool_false; | |||
343 | switch (expr1->type) { | |||
344 | case isl_ast_expr_int: | |||
345 | return isl_val_eq(expr1->u.v, expr2->u.v); | |||
346 | case isl_ast_expr_id: | |||
347 | return expr1->u.id == expr2->u.id; | |||
348 | case isl_ast_expr_op: | |||
349 | if (expr1->u.op.op != expr2->u.op.op) | |||
350 | return isl_bool_false; | |||
351 | if (expr1->u.op.n_arg != expr2->u.op.n_arg) | |||
352 | return isl_bool_false; | |||
353 | for (i = 0; i < expr1->u.op.n_arg; ++i) { | |||
354 | isl_bool equal; | |||
355 | equal = isl_ast_expr_is_equal(expr1->u.op.args[i], | |||
356 | expr2->u.op.args[i]); | |||
357 | if (equal < 0 || !equal) | |||
358 | return equal; | |||
359 | } | |||
360 | return 1; | |||
361 | case isl_ast_expr_error: | |||
362 | return isl_bool_error; | |||
363 | } | |||
364 | ||||
365 | isl_die(isl_ast_expr_get_ctx(expr1), isl_error_internal,do { isl_handle_error(isl_ast_expr_get_ctx(expr1), isl_error_internal , "unhandled case", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 366); return isl_bool_error; } while (0) | |||
366 | "unhandled case", return isl_bool_error)do { isl_handle_error(isl_ast_expr_get_ctx(expr1), isl_error_internal , "unhandled case", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 366); return isl_bool_error; } while (0); | |||
367 | } | |||
368 | ||||
369 | /* Create a new operation expression of operation type "op", | |||
370 | * with "n_arg" as yet unspecified arguments. | |||
371 | */ | |||
372 | __isl_give isl_ast_expr *isl_ast_expr_alloc_op(isl_ctx *ctx, | |||
373 | enum isl_ast_op_type op, int n_arg) | |||
374 | { | |||
375 | isl_ast_expr *expr; | |||
376 | ||||
377 | expr = isl_calloc_type(ctx, isl_ast_expr)((isl_ast_expr *)isl_calloc_or_die(ctx, 1, sizeof(isl_ast_expr ))); | |||
378 | if (!expr) | |||
379 | return NULL((void*)0); | |||
380 | ||||
381 | expr->ctx = ctx; | |||
382 | isl_ctx_ref(ctx); | |||
383 | expr->ref = 1; | |||
384 | expr->type = isl_ast_expr_op; | |||
385 | expr->u.op.op = op; | |||
386 | expr->u.op.n_arg = n_arg; | |||
387 | expr->u.op.args = isl_calloc_array(ctx, isl_ast_expr *, n_arg)((isl_ast_expr * *)isl_calloc_or_die(ctx, n_arg, sizeof(isl_ast_expr *))); | |||
388 | ||||
389 | if (n_arg && !expr->u.op.args) | |||
390 | return isl_ast_expr_free(expr); | |||
391 | ||||
392 | return expr; | |||
393 | } | |||
394 | ||||
395 | /* Create a new id expression representing "id". | |||
396 | */ | |||
397 | __isl_give isl_ast_expr *isl_ast_expr_from_id(__isl_take isl_id *id) | |||
398 | { | |||
399 | isl_ctx *ctx; | |||
400 | isl_ast_expr *expr; | |||
401 | ||||
402 | if (!id) | |||
403 | return NULL((void*)0); | |||
404 | ||||
405 | ctx = isl_id_get_ctx(id); | |||
406 | expr = isl_calloc_type(ctx, isl_ast_expr)((isl_ast_expr *)isl_calloc_or_die(ctx, 1, sizeof(isl_ast_expr ))); | |||
407 | if (!expr) | |||
408 | goto error; | |||
409 | ||||
410 | expr->ctx = ctx; | |||
411 | isl_ctx_ref(ctx); | |||
412 | expr->ref = 1; | |||
413 | expr->type = isl_ast_expr_id; | |||
414 | expr->u.id = id; | |||
415 | ||||
416 | return expr; | |||
417 | error: | |||
418 | isl_id_free(id); | |||
419 | return NULL((void*)0); | |||
420 | } | |||
421 | ||||
422 | /* Create a new integer expression representing "i". | |||
423 | */ | |||
424 | __isl_give isl_ast_expr *isl_ast_expr_alloc_int_si(isl_ctx *ctx, int i) | |||
425 | { | |||
426 | isl_ast_expr *expr; | |||
427 | ||||
428 | expr = isl_calloc_type(ctx, isl_ast_expr)((isl_ast_expr *)isl_calloc_or_die(ctx, 1, sizeof(isl_ast_expr ))); | |||
429 | if (!expr) | |||
430 | return NULL((void*)0); | |||
431 | ||||
432 | expr->ctx = ctx; | |||
433 | isl_ctx_ref(ctx); | |||
434 | expr->ref = 1; | |||
435 | expr->type = isl_ast_expr_int; | |||
436 | expr->u.v = isl_val_int_from_si(ctx, i); | |||
437 | if (!expr->u.v) | |||
438 | return isl_ast_expr_free(expr); | |||
439 | ||||
440 | return expr; | |||
441 | } | |||
442 | ||||
443 | /* Create a new integer expression representing "v". | |||
444 | */ | |||
445 | __isl_give isl_ast_expr *isl_ast_expr_from_val(__isl_take isl_val *v) | |||
446 | { | |||
447 | isl_ctx *ctx; | |||
448 | isl_ast_expr *expr; | |||
449 | ||||
450 | if (!v) | |||
451 | return NULL((void*)0); | |||
452 | if (!isl_val_is_int(v)) | |||
453 | isl_die(isl_val_get_ctx(v), isl_error_invalid,do { isl_handle_error(isl_val_get_ctx(v), isl_error_invalid, "expecting integer value" , "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 454); goto error; } while (0) | |||
454 | "expecting integer value", goto error)do { isl_handle_error(isl_val_get_ctx(v), isl_error_invalid, "expecting integer value" , "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 454); goto error; } while (0); | |||
455 | ||||
456 | ctx = isl_val_get_ctx(v); | |||
457 | expr = isl_calloc_type(ctx, isl_ast_expr)((isl_ast_expr *)isl_calloc_or_die(ctx, 1, sizeof(isl_ast_expr ))); | |||
458 | if (!expr) | |||
459 | goto error; | |||
460 | ||||
461 | expr->ctx = ctx; | |||
462 | isl_ctx_ref(ctx); | |||
463 | expr->ref = 1; | |||
464 | expr->type = isl_ast_expr_int; | |||
465 | expr->u.v = v; | |||
466 | ||||
467 | return expr; | |||
468 | error: | |||
469 | isl_val_free(v); | |||
470 | return NULL((void*)0); | |||
471 | } | |||
472 | ||||
473 | /* Create an expression representing the unary operation "type" applied to | |||
474 | * "arg". | |||
475 | */ | |||
476 | __isl_give isl_ast_expr *isl_ast_expr_alloc_unary(enum isl_ast_op_type type, | |||
477 | __isl_take isl_ast_expr *arg) | |||
478 | { | |||
479 | isl_ctx *ctx; | |||
480 | isl_ast_expr *expr = NULL((void*)0); | |||
481 | ||||
482 | if (!arg) | |||
483 | return NULL((void*)0); | |||
484 | ||||
485 | ctx = isl_ast_expr_get_ctx(arg); | |||
486 | expr = isl_ast_expr_alloc_op(ctx, type, 1); | |||
487 | if (!expr) | |||
488 | goto error; | |||
489 | ||||
490 | expr->u.op.args[0] = arg; | |||
491 | ||||
492 | return expr; | |||
493 | error: | |||
494 | isl_ast_expr_free(arg); | |||
495 | return NULL((void*)0); | |||
496 | } | |||
497 | ||||
498 | /* Create an expression representing the negation of "arg". | |||
499 | */ | |||
500 | __isl_give isl_ast_expr *isl_ast_expr_neg(__isl_take isl_ast_expr *arg) | |||
501 | { | |||
502 | return isl_ast_expr_alloc_unary(isl_ast_op_minus, arg); | |||
503 | } | |||
504 | ||||
505 | /* Create an expression representing the address of "expr". | |||
506 | */ | |||
507 | __isl_give isl_ast_expr *isl_ast_expr_address_of(__isl_take isl_ast_expr *expr) | |||
508 | { | |||
509 | if (!expr) | |||
510 | return NULL((void*)0); | |||
511 | ||||
512 | if (isl_ast_expr_get_type(expr) != isl_ast_expr_op || | |||
513 | isl_ast_expr_get_op_type(expr) != isl_ast_op_access) | |||
514 | isl_die(isl_ast_expr_get_ctx(expr), isl_error_invalid,do { isl_handle_error(isl_ast_expr_get_ctx(expr), isl_error_invalid , "can only take address of access expressions", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 516); return isl_ast_expr_free(expr); } while (0) | |||
515 | "can only take address of access expressions",do { isl_handle_error(isl_ast_expr_get_ctx(expr), isl_error_invalid , "can only take address of access expressions", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 516); return isl_ast_expr_free(expr); } while (0) | |||
516 | return isl_ast_expr_free(expr))do { isl_handle_error(isl_ast_expr_get_ctx(expr), isl_error_invalid , "can only take address of access expressions", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 516); return isl_ast_expr_free(expr); } while (0); | |||
517 | ||||
518 | return isl_ast_expr_alloc_unary(isl_ast_op_address_of, expr); | |||
519 | } | |||
520 | ||||
521 | /* Create an expression representing the binary operation "type" | |||
522 | * applied to "expr1" and "expr2". | |||
523 | */ | |||
524 | __isl_give isl_ast_expr *isl_ast_expr_alloc_binary(enum isl_ast_op_type type, | |||
525 | __isl_take isl_ast_expr *expr1, __isl_take isl_ast_expr *expr2) | |||
526 | { | |||
527 | isl_ctx *ctx; | |||
528 | isl_ast_expr *expr = NULL((void*)0); | |||
529 | ||||
530 | if (!expr1 || !expr2) | |||
531 | goto error; | |||
532 | ||||
533 | ctx = isl_ast_expr_get_ctx(expr1); | |||
534 | expr = isl_ast_expr_alloc_op(ctx, type, 2); | |||
535 | if (!expr) | |||
536 | goto error; | |||
537 | ||||
538 | expr->u.op.args[0] = expr1; | |||
539 | expr->u.op.args[1] = expr2; | |||
540 | ||||
541 | return expr; | |||
542 | error: | |||
543 | isl_ast_expr_free(expr1); | |||
544 | isl_ast_expr_free(expr2); | |||
545 | return NULL((void*)0); | |||
546 | } | |||
547 | ||||
548 | /* Create an expression representing the sum of "expr1" and "expr2". | |||
549 | */ | |||
550 | __isl_give isl_ast_expr *isl_ast_expr_add(__isl_take isl_ast_expr *expr1, | |||
551 | __isl_take isl_ast_expr *expr2) | |||
552 | { | |||
553 | return isl_ast_expr_alloc_binary(isl_ast_op_add, expr1, expr2); | |||
554 | } | |||
555 | ||||
556 | /* Create an expression representing the difference of "expr1" and "expr2". | |||
557 | */ | |||
558 | __isl_give isl_ast_expr *isl_ast_expr_sub(__isl_take isl_ast_expr *expr1, | |||
559 | __isl_take isl_ast_expr *expr2) | |||
560 | { | |||
561 | return isl_ast_expr_alloc_binary(isl_ast_op_sub, expr1, expr2); | |||
562 | } | |||
563 | ||||
564 | /* Create an expression representing the product of "expr1" and "expr2". | |||
565 | */ | |||
566 | __isl_give isl_ast_expr *isl_ast_expr_mul(__isl_take isl_ast_expr *expr1, | |||
567 | __isl_take isl_ast_expr *expr2) | |||
568 | { | |||
569 | return isl_ast_expr_alloc_binary(isl_ast_op_mul, expr1, expr2); | |||
570 | } | |||
571 | ||||
572 | /* Create an expression representing the quotient of "expr1" and "expr2". | |||
573 | */ | |||
574 | __isl_give isl_ast_expr *isl_ast_expr_div(__isl_take isl_ast_expr *expr1, | |||
575 | __isl_take isl_ast_expr *expr2) | |||
576 | { | |||
577 | return isl_ast_expr_alloc_binary(isl_ast_op_div, expr1, expr2); | |||
578 | } | |||
579 | ||||
580 | /* Create an expression representing the quotient of the integer | |||
581 | * division of "expr1" by "expr2", where "expr1" is known to be | |||
582 | * non-negative. | |||
583 | */ | |||
584 | __isl_give isl_ast_expr *isl_ast_expr_pdiv_q(__isl_take isl_ast_expr *expr1, | |||
585 | __isl_take isl_ast_expr *expr2) | |||
586 | { | |||
587 | return isl_ast_expr_alloc_binary(isl_ast_op_pdiv_q, expr1, expr2); | |||
588 | } | |||
589 | ||||
590 | /* Create an expression representing the remainder of the integer | |||
591 | * division of "expr1" by "expr2", where "expr1" is known to be | |||
592 | * non-negative. | |||
593 | */ | |||
594 | __isl_give isl_ast_expr *isl_ast_expr_pdiv_r(__isl_take isl_ast_expr *expr1, | |||
595 | __isl_take isl_ast_expr *expr2) | |||
596 | { | |||
597 | return isl_ast_expr_alloc_binary(isl_ast_op_pdiv_r, expr1, expr2); | |||
598 | } | |||
599 | ||||
600 | /* Create an expression representing the conjunction of "expr1" and "expr2". | |||
601 | */ | |||
602 | __isl_give isl_ast_expr *isl_ast_expr_and(__isl_take isl_ast_expr *expr1, | |||
603 | __isl_take isl_ast_expr *expr2) | |||
604 | { | |||
605 | return isl_ast_expr_alloc_binary(isl_ast_op_and, expr1, expr2); | |||
606 | } | |||
607 | ||||
608 | /* Create an expression representing the conjunction of "expr1" and "expr2", | |||
609 | * where "expr2" is evaluated only if "expr1" is evaluated to true. | |||
610 | */ | |||
611 | __isl_give isl_ast_expr *isl_ast_expr_and_then(__isl_take isl_ast_expr *expr1, | |||
612 | __isl_take isl_ast_expr *expr2) | |||
613 | { | |||
614 | return isl_ast_expr_alloc_binary(isl_ast_op_and_then, expr1, expr2); | |||
615 | } | |||
616 | ||||
617 | /* Create an expression representing the disjunction of "expr1" and "expr2". | |||
618 | */ | |||
619 | __isl_give isl_ast_expr *isl_ast_expr_or(__isl_take isl_ast_expr *expr1, | |||
620 | __isl_take isl_ast_expr *expr2) | |||
621 | { | |||
622 | return isl_ast_expr_alloc_binary(isl_ast_op_or, expr1, expr2); | |||
623 | } | |||
624 | ||||
625 | /* Create an expression representing the disjunction of "expr1" and "expr2", | |||
626 | * where "expr2" is evaluated only if "expr1" is evaluated to false. | |||
627 | */ | |||
628 | __isl_give isl_ast_expr *isl_ast_expr_or_else(__isl_take isl_ast_expr *expr1, | |||
629 | __isl_take isl_ast_expr *expr2) | |||
630 | { | |||
631 | return isl_ast_expr_alloc_binary(isl_ast_op_or_else, expr1, expr2); | |||
632 | } | |||
633 | ||||
634 | /* Create an expression representing "expr1" less than or equal to "expr2". | |||
635 | */ | |||
636 | __isl_give isl_ast_expr *isl_ast_expr_le(__isl_take isl_ast_expr *expr1, | |||
637 | __isl_take isl_ast_expr *expr2) | |||
638 | { | |||
639 | return isl_ast_expr_alloc_binary(isl_ast_op_le, expr1, expr2); | |||
640 | } | |||
641 | ||||
642 | /* Create an expression representing "expr1" less than "expr2". | |||
643 | */ | |||
644 | __isl_give isl_ast_expr *isl_ast_expr_lt(__isl_take isl_ast_expr *expr1, | |||
645 | __isl_take isl_ast_expr *expr2) | |||
646 | { | |||
647 | return isl_ast_expr_alloc_binary(isl_ast_op_lt, expr1, expr2); | |||
648 | } | |||
649 | ||||
650 | /* Create an expression representing "expr1" greater than or equal to "expr2". | |||
651 | */ | |||
652 | __isl_give isl_ast_expr *isl_ast_expr_ge(__isl_take isl_ast_expr *expr1, | |||
653 | __isl_take isl_ast_expr *expr2) | |||
654 | { | |||
655 | return isl_ast_expr_alloc_binary(isl_ast_op_ge, expr1, expr2); | |||
656 | } | |||
657 | ||||
658 | /* Create an expression representing "expr1" greater than "expr2". | |||
659 | */ | |||
660 | __isl_give isl_ast_expr *isl_ast_expr_gt(__isl_take isl_ast_expr *expr1, | |||
661 | __isl_take isl_ast_expr *expr2) | |||
662 | { | |||
663 | return isl_ast_expr_alloc_binary(isl_ast_op_gt, expr1, expr2); | |||
664 | } | |||
665 | ||||
666 | /* Create an expression representing "expr1" equal to "expr2". | |||
667 | */ | |||
668 | __isl_give isl_ast_expr *isl_ast_expr_eq(__isl_take isl_ast_expr *expr1, | |||
669 | __isl_take isl_ast_expr *expr2) | |||
670 | { | |||
671 | return isl_ast_expr_alloc_binary(isl_ast_op_eq, expr1, expr2); | |||
672 | } | |||
673 | ||||
674 | /* Create an expression of type "type" with as arguments "arg0" followed | |||
675 | * by "arguments". | |||
676 | */ | |||
677 | static __isl_give isl_ast_expr *ast_expr_with_arguments( | |||
678 | enum isl_ast_op_type type, __isl_take isl_ast_expr *arg0, | |||
679 | __isl_take isl_ast_expr_list *arguments) | |||
680 | { | |||
681 | int i, n; | |||
682 | isl_ctx *ctx; | |||
683 | isl_ast_expr *res = NULL((void*)0); | |||
684 | ||||
685 | if (!arg0 || !arguments) | |||
686 | goto error; | |||
687 | ||||
688 | ctx = isl_ast_expr_get_ctx(arg0); | |||
689 | n = isl_ast_expr_list_n_ast_expr(arguments); | |||
690 | res = isl_ast_expr_alloc_op(ctx, type, 1 + n); | |||
691 | if (!res) | |||
692 | goto error; | |||
693 | for (i = 0; i < n; ++i) { | |||
694 | isl_ast_expr *arg; | |||
695 | arg = isl_ast_expr_list_get_ast_expr(arguments, i); | |||
696 | res->u.op.args[1 + i] = arg; | |||
697 | if (!arg) | |||
698 | goto error; | |||
699 | } | |||
700 | res->u.op.args[0] = arg0; | |||
701 | ||||
702 | isl_ast_expr_list_free(arguments); | |||
703 | return res; | |||
704 | error: | |||
705 | isl_ast_expr_free(arg0); | |||
706 | isl_ast_expr_list_free(arguments); | |||
707 | isl_ast_expr_free(res); | |||
708 | return NULL((void*)0); | |||
709 | } | |||
710 | ||||
711 | /* Create an expression representing an access to "array" with index | |||
712 | * expressions "indices". | |||
713 | */ | |||
714 | __isl_give isl_ast_expr *isl_ast_expr_access(__isl_take isl_ast_expr *array, | |||
715 | __isl_take isl_ast_expr_list *indices) | |||
716 | { | |||
717 | return ast_expr_with_arguments(isl_ast_op_access, array, indices); | |||
718 | } | |||
719 | ||||
720 | /* Create an expression representing a call to "function" with argument | |||
721 | * expressions "arguments". | |||
722 | */ | |||
723 | __isl_give isl_ast_expr *isl_ast_expr_call(__isl_take isl_ast_expr *function, | |||
724 | __isl_take isl_ast_expr_list *arguments) | |||
725 | { | |||
726 | return ast_expr_with_arguments(isl_ast_op_call, function, arguments); | |||
727 | } | |||
728 | ||||
729 | /* For each subexpression of "expr" of type isl_ast_expr_id, | |||
730 | * if it appears in "id2expr", then replace it by the corresponding | |||
731 | * expression. | |||
732 | */ | |||
733 | __isl_give isl_ast_expr *isl_ast_expr_substitute_ids( | |||
734 | __isl_take isl_ast_expr *expr, __isl_take isl_id_to_ast_expr *id2expr) | |||
735 | { | |||
736 | int i; | |||
737 | isl_maybe_isl_ast_expr m; | |||
738 | ||||
739 | if (!expr || !id2expr) | |||
740 | goto error; | |||
741 | ||||
742 | switch (expr->type) { | |||
743 | case isl_ast_expr_int: | |||
744 | break; | |||
745 | case isl_ast_expr_id: | |||
746 | m = isl_id_to_ast_expr_try_get(id2expr, expr->u.id); | |||
747 | if (m.valid < 0) | |||
748 | goto error; | |||
749 | if (!m.valid) | |||
750 | break; | |||
751 | isl_ast_expr_free(expr); | |||
752 | expr = m.value; | |||
753 | break; | |||
754 | case isl_ast_expr_op: | |||
755 | for (i = 0; i < expr->u.op.n_arg; ++i) { | |||
756 | isl_ast_expr *arg; | |||
757 | arg = isl_ast_expr_copy(expr->u.op.args[i]); | |||
758 | arg = isl_ast_expr_substitute_ids(arg, | |||
759 | isl_id_to_ast_expr_copy(id2expr)); | |||
760 | if (arg == expr->u.op.args[i]) { | |||
761 | isl_ast_expr_free(arg); | |||
762 | continue; | |||
763 | } | |||
764 | if (!arg) | |||
765 | expr = isl_ast_expr_free(expr); | |||
766 | expr = isl_ast_expr_cow(expr); | |||
767 | if (!expr) { | |||
768 | isl_ast_expr_free(arg); | |||
769 | break; | |||
770 | } | |||
771 | isl_ast_expr_free(expr->u.op.args[i]); | |||
772 | expr->u.op.args[i] = arg; | |||
773 | } | |||
774 | break; | |||
775 | case isl_ast_expr_error: | |||
776 | expr = isl_ast_expr_free(expr); | |||
777 | break; | |||
778 | } | |||
779 | ||||
780 | isl_id_to_ast_expr_free(id2expr); | |||
781 | return expr; | |||
782 | error: | |||
783 | isl_ast_expr_free(expr); | |||
784 | isl_id_to_ast_expr_free(id2expr); | |||
785 | return NULL((void*)0); | |||
786 | } | |||
787 | ||||
788 | isl_ctx *isl_ast_node_get_ctx(__isl_keep isl_ast_node *node) | |||
789 | { | |||
790 | return node ? node->ctx : NULL((void*)0); | |||
791 | } | |||
792 | ||||
793 | enum isl_ast_node_type isl_ast_node_get_type(__isl_keep isl_ast_node *node) | |||
794 | { | |||
795 | return node ? node->type : isl_ast_node_error; | |||
796 | } | |||
797 | ||||
798 | __isl_give isl_ast_node *isl_ast_node_alloc(isl_ctx *ctx, | |||
799 | enum isl_ast_node_type type) | |||
800 | { | |||
801 | isl_ast_node *node; | |||
802 | ||||
803 | node = isl_calloc_type(ctx, isl_ast_node)((isl_ast_node *)isl_calloc_or_die(ctx, 1, sizeof(isl_ast_node ))); | |||
804 | if (!node) | |||
805 | return NULL((void*)0); | |||
806 | ||||
807 | node->ctx = ctx; | |||
808 | isl_ctx_ref(ctx); | |||
809 | node->ref = 1; | |||
810 | node->type = type; | |||
811 | ||||
812 | return node; | |||
813 | } | |||
814 | ||||
815 | /* Create an if node with the given guard. | |||
816 | * | |||
817 | * The then body needs to be filled in later. | |||
818 | */ | |||
819 | __isl_give isl_ast_node *isl_ast_node_alloc_if(__isl_take isl_ast_expr *guard) | |||
820 | { | |||
821 | isl_ast_node *node; | |||
822 | ||||
823 | if (!guard) | |||
824 | return NULL((void*)0); | |||
825 | ||||
826 | node = isl_ast_node_alloc(isl_ast_expr_get_ctx(guard), isl_ast_node_if); | |||
827 | if (!node) | |||
828 | goto error; | |||
829 | node->u.i.guard = guard; | |||
830 | ||||
831 | return node; | |||
832 | error: | |||
833 | isl_ast_expr_free(guard); | |||
834 | return NULL((void*)0); | |||
835 | } | |||
836 | ||||
837 | /* Create a for node with the given iterator. | |||
838 | * | |||
839 | * The remaining fields need to be filled in later. | |||
840 | */ | |||
841 | __isl_give isl_ast_node *isl_ast_node_alloc_for(__isl_take isl_id *id) | |||
842 | { | |||
843 | isl_ast_node *node; | |||
844 | isl_ctx *ctx; | |||
845 | ||||
846 | if (!id) | |||
847 | return NULL((void*)0); | |||
848 | ||||
849 | ctx = isl_id_get_ctx(id); | |||
850 | node = isl_ast_node_alloc(ctx, isl_ast_node_for); | |||
851 | if (!node) | |||
852 | goto error; | |||
853 | ||||
854 | node->u.f.iterator = isl_ast_expr_from_id(id); | |||
855 | if (!node->u.f.iterator) | |||
856 | return isl_ast_node_free(node); | |||
857 | ||||
858 | return node; | |||
859 | error: | |||
860 | isl_id_free(id); | |||
861 | return NULL((void*)0); | |||
862 | } | |||
863 | ||||
864 | /* Create a mark node, marking "node" with "id". | |||
865 | */ | |||
866 | __isl_give isl_ast_node *isl_ast_node_alloc_mark(__isl_take isl_id *id, | |||
867 | __isl_take isl_ast_node *node) | |||
868 | { | |||
869 | isl_ctx *ctx; | |||
870 | isl_ast_node *mark; | |||
871 | ||||
872 | if (!id || !node) | |||
873 | goto error; | |||
874 | ||||
875 | ctx = isl_id_get_ctx(id); | |||
876 | mark = isl_ast_node_alloc(ctx, isl_ast_node_mark); | |||
877 | if (!mark) | |||
878 | goto error; | |||
879 | ||||
880 | mark->u.m.mark = id; | |||
881 | mark->u.m.node = node; | |||
882 | ||||
883 | return mark; | |||
884 | error: | |||
885 | isl_id_free(id); | |||
886 | isl_ast_node_free(node); | |||
887 | return NULL((void*)0); | |||
888 | } | |||
889 | ||||
890 | /* Create a user node evaluating "expr". | |||
891 | */ | |||
892 | __isl_give isl_ast_node *isl_ast_node_alloc_user(__isl_take isl_ast_expr *expr) | |||
893 | { | |||
894 | isl_ctx *ctx; | |||
895 | isl_ast_node *node; | |||
896 | ||||
897 | if (!expr) | |||
898 | return NULL((void*)0); | |||
899 | ||||
900 | ctx = isl_ast_expr_get_ctx(expr); | |||
901 | node = isl_ast_node_alloc(ctx, isl_ast_node_user); | |||
902 | if (!node) | |||
903 | goto error; | |||
904 | ||||
905 | node->u.e.expr = expr; | |||
906 | ||||
907 | return node; | |||
908 | error: | |||
909 | isl_ast_expr_free(expr); | |||
910 | return NULL((void*)0); | |||
911 | } | |||
912 | ||||
913 | /* Create a block node with the given children. | |||
914 | */ | |||
915 | __isl_give isl_ast_node *isl_ast_node_alloc_block( | |||
916 | __isl_take isl_ast_node_list *list) | |||
917 | { | |||
918 | isl_ast_node *node; | |||
919 | isl_ctx *ctx; | |||
920 | ||||
921 | if (!list) | |||
922 | return NULL((void*)0); | |||
923 | ||||
924 | ctx = isl_ast_node_list_get_ctx(list); | |||
925 | node = isl_ast_node_alloc(ctx, isl_ast_node_block); | |||
926 | if (!node) | |||
927 | goto error; | |||
928 | ||||
929 | node->u.b.children = list; | |||
930 | ||||
931 | return node; | |||
932 | error: | |||
933 | isl_ast_node_list_free(list); | |||
934 | return NULL((void*)0); | |||
935 | } | |||
936 | ||||
937 | /* Represent the given list of nodes as a single node, either by | |||
938 | * extract the node from a single element list or by creating | |||
939 | * a block node with the list of nodes as children. | |||
940 | */ | |||
941 | __isl_give isl_ast_node *isl_ast_node_from_ast_node_list( | |||
942 | __isl_take isl_ast_node_list *list) | |||
943 | { | |||
944 | isl_ast_node *node; | |||
945 | ||||
946 | if (isl_ast_node_list_n_ast_node(list) != 1) | |||
947 | return isl_ast_node_alloc_block(list); | |||
948 | ||||
949 | node = isl_ast_node_list_get_ast_node(list, 0); | |||
950 | isl_ast_node_list_free(list); | |||
951 | ||||
952 | return node; | |||
953 | } | |||
954 | ||||
955 | __isl_give isl_ast_node *isl_ast_node_copy(__isl_keep isl_ast_node *node) | |||
956 | { | |||
957 | if (!node) | |||
958 | return NULL((void*)0); | |||
959 | ||||
960 | node->ref++; | |||
961 | return node; | |||
962 | } | |||
963 | ||||
964 | __isl_give isl_ast_node *isl_ast_node_dup(__isl_keep isl_ast_node *node) | |||
965 | { | |||
966 | isl_ast_node *dup; | |||
967 | ||||
968 | if (!node) | |||
969 | return NULL((void*)0); | |||
970 | ||||
971 | dup = isl_ast_node_alloc(isl_ast_node_get_ctx(node), node->type); | |||
972 | if (!dup) | |||
973 | return NULL((void*)0); | |||
974 | ||||
975 | switch (node->type) { | |||
976 | case isl_ast_node_if: | |||
977 | dup->u.i.guard = isl_ast_expr_copy(node->u.i.guard); | |||
978 | dup->u.i.then = isl_ast_node_copy(node->u.i.then); | |||
979 | dup->u.i.else_node = isl_ast_node_copy(node->u.i.else_node); | |||
980 | if (!dup->u.i.guard || !dup->u.i.then || | |||
981 | (node->u.i.else_node && !dup->u.i.else_node)) | |||
982 | return isl_ast_node_free(dup); | |||
983 | break; | |||
984 | case isl_ast_node_for: | |||
985 | dup->u.f.iterator = isl_ast_expr_copy(node->u.f.iterator); | |||
986 | dup->u.f.init = isl_ast_expr_copy(node->u.f.init); | |||
987 | dup->u.f.cond = isl_ast_expr_copy(node->u.f.cond); | |||
988 | dup->u.f.inc = isl_ast_expr_copy(node->u.f.inc); | |||
989 | dup->u.f.body = isl_ast_node_copy(node->u.f.body); | |||
990 | if (!dup->u.f.iterator || !dup->u.f.init || !dup->u.f.cond || | |||
991 | !dup->u.f.inc || !dup->u.f.body) | |||
992 | return isl_ast_node_free(dup); | |||
993 | break; | |||
994 | case isl_ast_node_block: | |||
995 | dup->u.b.children = isl_ast_node_list_copy(node->u.b.children); | |||
996 | if (!dup->u.b.children) | |||
997 | return isl_ast_node_free(dup); | |||
998 | break; | |||
999 | case isl_ast_node_mark: | |||
1000 | dup->u.m.mark = isl_id_copy(node->u.m.mark); | |||
1001 | dup->u.m.node = isl_ast_node_copy(node->u.m.node); | |||
1002 | if (!dup->u.m.mark || !dup->u.m.node) | |||
1003 | return isl_ast_node_free(dup); | |||
1004 | break; | |||
1005 | case isl_ast_node_user: | |||
1006 | dup->u.e.expr = isl_ast_expr_copy(node->u.e.expr); | |||
1007 | if (!dup->u.e.expr) | |||
1008 | return isl_ast_node_free(dup); | |||
1009 | break; | |||
1010 | case isl_ast_node_error: | |||
1011 | break; | |||
1012 | } | |||
1013 | ||||
1014 | return dup; | |||
1015 | } | |||
1016 | ||||
1017 | __isl_give isl_ast_node *isl_ast_node_cow(__isl_take isl_ast_node *node) | |||
1018 | { | |||
1019 | if (!node) | |||
1020 | return NULL((void*)0); | |||
1021 | ||||
1022 | if (node->ref == 1) | |||
1023 | return node; | |||
1024 | node->ref--; | |||
1025 | return isl_ast_node_dup(node); | |||
1026 | } | |||
1027 | ||||
1028 | __isl_null isl_ast_node *isl_ast_node_free(__isl_take isl_ast_node *node) | |||
1029 | { | |||
1030 | if (!node) | |||
1031 | return NULL((void*)0); | |||
1032 | ||||
1033 | if (--node->ref > 0) | |||
1034 | return NULL((void*)0); | |||
1035 | ||||
1036 | switch (node->type) { | |||
1037 | case isl_ast_node_if: | |||
1038 | isl_ast_expr_free(node->u.i.guard); | |||
1039 | isl_ast_node_free(node->u.i.then); | |||
1040 | isl_ast_node_free(node->u.i.else_node); | |||
1041 | break; | |||
1042 | case isl_ast_node_for: | |||
1043 | isl_ast_expr_free(node->u.f.iterator); | |||
1044 | isl_ast_expr_free(node->u.f.init); | |||
1045 | isl_ast_expr_free(node->u.f.cond); | |||
1046 | isl_ast_expr_free(node->u.f.inc); | |||
1047 | isl_ast_node_free(node->u.f.body); | |||
1048 | break; | |||
1049 | case isl_ast_node_block: | |||
1050 | isl_ast_node_list_free(node->u.b.children); | |||
1051 | break; | |||
1052 | case isl_ast_node_mark: | |||
1053 | isl_id_free(node->u.m.mark); | |||
1054 | isl_ast_node_free(node->u.m.node); | |||
1055 | break; | |||
1056 | case isl_ast_node_user: | |||
1057 | isl_ast_expr_free(node->u.e.expr); | |||
1058 | break; | |||
1059 | case isl_ast_node_error: | |||
1060 | break; | |||
1061 | } | |||
1062 | ||||
1063 | isl_id_free(node->annotation); | |||
1064 | isl_ctx_deref(node->ctx); | |||
1065 | free(node); | |||
1066 | ||||
1067 | return NULL((void*)0); | |||
1068 | } | |||
1069 | ||||
1070 | /* Replace the body of the for node "node" by "body". | |||
1071 | */ | |||
1072 | __isl_give isl_ast_node *isl_ast_node_for_set_body( | |||
1073 | __isl_take isl_ast_node *node, __isl_take isl_ast_node *body) | |||
1074 | { | |||
1075 | node = isl_ast_node_cow(node); | |||
1076 | if (!node || !body) | |||
1077 | goto error; | |||
1078 | if (node->type != isl_ast_node_for) | |||
1079 | isl_die(isl_ast_node_get_ctx(node), isl_error_invalid,do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a for node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1080); goto error; } while (0) | |||
1080 | "not a for node", goto error)do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a for node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1080); goto error; } while (0); | |||
1081 | ||||
1082 | isl_ast_node_free(node->u.f.body); | |||
1083 | node->u.f.body = body; | |||
1084 | ||||
1085 | return node; | |||
1086 | error: | |||
1087 | isl_ast_node_free(node); | |||
1088 | isl_ast_node_free(body); | |||
1089 | return NULL((void*)0); | |||
1090 | } | |||
1091 | ||||
1092 | __isl_give isl_ast_node *isl_ast_node_for_get_body( | |||
1093 | __isl_keep isl_ast_node *node) | |||
1094 | { | |||
1095 | if (!node) | |||
1096 | return NULL((void*)0); | |||
1097 | if (node->type != isl_ast_node_for) | |||
1098 | isl_die(isl_ast_node_get_ctx(node), isl_error_invalid,do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a for node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1099); return ((void*)0); } while (0) | |||
1099 | "not a for node", return NULL)do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a for node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1099); return ((void*)0); } while (0); | |||
1100 | return isl_ast_node_copy(node->u.f.body); | |||
1101 | } | |||
1102 | ||||
1103 | /* Mark the given for node as being degenerate. | |||
1104 | */ | |||
1105 | __isl_give isl_ast_node *isl_ast_node_for_mark_degenerate( | |||
1106 | __isl_take isl_ast_node *node) | |||
1107 | { | |||
1108 | node = isl_ast_node_cow(node); | |||
1109 | if (!node) | |||
1110 | return NULL((void*)0); | |||
1111 | node->u.f.degenerate = 1; | |||
1112 | return node; | |||
1113 | } | |||
1114 | ||||
1115 | isl_bool isl_ast_node_for_is_degenerate(__isl_keep isl_ast_node *node) | |||
1116 | { | |||
1117 | if (!node) | |||
1118 | return isl_bool_error; | |||
1119 | if (node->type != isl_ast_node_for) | |||
1120 | isl_die(isl_ast_node_get_ctx(node), isl_error_invalid,do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a for node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1121); return isl_bool_error; } while (0) | |||
1121 | "not a for node", return isl_bool_error)do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a for node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1121); return isl_bool_error; } while (0); | |||
1122 | return node->u.f.degenerate; | |||
1123 | } | |||
1124 | ||||
1125 | __isl_give isl_ast_expr *isl_ast_node_for_get_iterator( | |||
1126 | __isl_keep isl_ast_node *node) | |||
1127 | { | |||
1128 | if (!node) | |||
1129 | return NULL((void*)0); | |||
1130 | if (node->type != isl_ast_node_for) | |||
1131 | isl_die(isl_ast_node_get_ctx(node), isl_error_invalid,do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a for node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1132); return ((void*)0); } while (0) | |||
1132 | "not a for node", return NULL)do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a for node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1132); return ((void*)0); } while (0); | |||
1133 | return isl_ast_expr_copy(node->u.f.iterator); | |||
1134 | } | |||
1135 | ||||
1136 | __isl_give isl_ast_expr *isl_ast_node_for_get_init( | |||
1137 | __isl_keep isl_ast_node *node) | |||
1138 | { | |||
1139 | if (!node) | |||
1140 | return NULL((void*)0); | |||
1141 | if (node->type != isl_ast_node_for) | |||
1142 | isl_die(isl_ast_node_get_ctx(node), isl_error_invalid,do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a for node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1143); return ((void*)0); } while (0) | |||
1143 | "not a for node", return NULL)do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a for node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1143); return ((void*)0); } while (0); | |||
1144 | return isl_ast_expr_copy(node->u.f.init); | |||
1145 | } | |||
1146 | ||||
1147 | /* Return the condition expression of the given for node. | |||
1148 | * | |||
1149 | * If the for node is degenerate, then the condition is not explicitly | |||
1150 | * stored in the node. Instead, it is constructed as | |||
1151 | * | |||
1152 | * iterator <= init | |||
1153 | */ | |||
1154 | __isl_give isl_ast_expr *isl_ast_node_for_get_cond( | |||
1155 | __isl_keep isl_ast_node *node) | |||
1156 | { | |||
1157 | if (!node) | |||
1158 | return NULL((void*)0); | |||
1159 | if (node->type != isl_ast_node_for) | |||
1160 | isl_die(isl_ast_node_get_ctx(node), isl_error_invalid,do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a for node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1161); return ((void*)0); } while (0) | |||
1161 | "not a for node", return NULL)do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a for node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1161); return ((void*)0); } while (0); | |||
1162 | if (!node->u.f.degenerate) | |||
1163 | return isl_ast_expr_copy(node->u.f.cond); | |||
1164 | ||||
1165 | return isl_ast_expr_alloc_binary(isl_ast_op_le, | |||
1166 | isl_ast_expr_copy(node->u.f.iterator), | |||
1167 | isl_ast_expr_copy(node->u.f.init)); | |||
1168 | } | |||
1169 | ||||
1170 | /* Return the increment of the given for node. | |||
1171 | * | |||
1172 | * If the for node is degenerate, then the increment is not explicitly | |||
1173 | * stored in the node. We simply return "1". | |||
1174 | */ | |||
1175 | __isl_give isl_ast_expr *isl_ast_node_for_get_inc( | |||
1176 | __isl_keep isl_ast_node *node) | |||
1177 | { | |||
1178 | if (!node) | |||
1179 | return NULL((void*)0); | |||
1180 | if (node->type != isl_ast_node_for) | |||
1181 | isl_die(isl_ast_node_get_ctx(node), isl_error_invalid,do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a for node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1182); return ((void*)0); } while (0) | |||
1182 | "not a for node", return NULL)do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a for node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1182); return ((void*)0); } while (0); | |||
1183 | if (!node->u.f.degenerate) | |||
1184 | return isl_ast_expr_copy(node->u.f.inc); | |||
1185 | return isl_ast_expr_alloc_int_si(isl_ast_node_get_ctx(node), 1); | |||
1186 | } | |||
1187 | ||||
1188 | /* Replace the then branch of the if node "node" by "child". | |||
1189 | */ | |||
1190 | __isl_give isl_ast_node *isl_ast_node_if_set_then( | |||
1191 | __isl_take isl_ast_node *node, __isl_take isl_ast_node *child) | |||
1192 | { | |||
1193 | node = isl_ast_node_cow(node); | |||
1194 | if (!node || !child) | |||
1195 | goto error; | |||
1196 | if (node->type != isl_ast_node_if) | |||
1197 | isl_die(isl_ast_node_get_ctx(node), isl_error_invalid,do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not an if node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1198); goto error; } while (0) | |||
1198 | "not an if node", goto error)do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not an if node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1198); goto error; } while (0); | |||
1199 | ||||
1200 | isl_ast_node_free(node->u.i.then); | |||
1201 | node->u.i.then = child; | |||
1202 | ||||
1203 | return node; | |||
1204 | error: | |||
1205 | isl_ast_node_free(node); | |||
1206 | isl_ast_node_free(child); | |||
1207 | return NULL((void*)0); | |||
1208 | } | |||
1209 | ||||
1210 | __isl_give isl_ast_node *isl_ast_node_if_get_then( | |||
1211 | __isl_keep isl_ast_node *node) | |||
1212 | { | |||
1213 | if (!node) | |||
1214 | return NULL((void*)0); | |||
1215 | if (node->type != isl_ast_node_if) | |||
1216 | isl_die(isl_ast_node_get_ctx(node), isl_error_invalid,do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not an if node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1217); return ((void*)0); } while (0) | |||
1217 | "not an if node", return NULL)do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not an if node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1217); return ((void*)0); } while (0); | |||
1218 | return isl_ast_node_copy(node->u.i.then); | |||
1219 | } | |||
1220 | ||||
1221 | isl_bool isl_ast_node_if_has_else( | |||
1222 | __isl_keep isl_ast_node *node) | |||
1223 | { | |||
1224 | if (!node) | |||
1225 | return isl_bool_error; | |||
1226 | if (node->type != isl_ast_node_if) | |||
1227 | isl_die(isl_ast_node_get_ctx(node), isl_error_invalid,do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not an if node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1228); return isl_bool_error; } while (0) | |||
1228 | "not an if node", return isl_bool_error)do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not an if node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1228); return isl_bool_error; } while (0); | |||
1229 | return node->u.i.else_node != NULL((void*)0); | |||
1230 | } | |||
1231 | ||||
1232 | __isl_give isl_ast_node *isl_ast_node_if_get_else( | |||
1233 | __isl_keep isl_ast_node *node) | |||
1234 | { | |||
1235 | if (!node) | |||
1236 | return NULL((void*)0); | |||
1237 | if (node->type != isl_ast_node_if) | |||
1238 | isl_die(isl_ast_node_get_ctx(node), isl_error_invalid,do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not an if node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1239); return ((void*)0); } while (0) | |||
1239 | "not an if node", return NULL)do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not an if node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1239); return ((void*)0); } while (0); | |||
1240 | return isl_ast_node_copy(node->u.i.else_node); | |||
1241 | } | |||
1242 | ||||
1243 | __isl_give isl_ast_expr *isl_ast_node_if_get_cond( | |||
1244 | __isl_keep isl_ast_node *node) | |||
1245 | { | |||
1246 | if (!node) | |||
1247 | return NULL((void*)0); | |||
1248 | if (node->type != isl_ast_node_if) | |||
1249 | isl_die(isl_ast_node_get_ctx(node), isl_error_invalid,do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a guard node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1250); return ((void*)0); } while (0) | |||
1250 | "not a guard node", return NULL)do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a guard node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1250); return ((void*)0); } while (0); | |||
1251 | return isl_ast_expr_copy(node->u.i.guard); | |||
1252 | } | |||
1253 | ||||
1254 | __isl_give isl_ast_node_list *isl_ast_node_block_get_children( | |||
1255 | __isl_keep isl_ast_node *node) | |||
1256 | { | |||
1257 | if (!node) | |||
1258 | return NULL((void*)0); | |||
1259 | if (node->type != isl_ast_node_block) | |||
1260 | isl_die(isl_ast_node_get_ctx(node), isl_error_invalid,do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a block node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1261); return ((void*)0); } while (0) | |||
1261 | "not a block node", return NULL)do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a block node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1261); return ((void*)0); } while (0); | |||
1262 | return isl_ast_node_list_copy(node->u.b.children); | |||
1263 | } | |||
1264 | ||||
1265 | __isl_give isl_ast_expr *isl_ast_node_user_get_expr( | |||
1266 | __isl_keep isl_ast_node *node) | |||
1267 | { | |||
1268 | if (!node) | |||
1269 | return NULL((void*)0); | |||
1270 | if (node->type != isl_ast_node_user) | |||
1271 | isl_die(isl_ast_node_get_ctx(node), isl_error_invalid,do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a user node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1272); return ((void*)0); } while (0) | |||
1272 | "not a user node", return NULL)do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a user node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1272); return ((void*)0); } while (0); | |||
1273 | ||||
1274 | return isl_ast_expr_copy(node->u.e.expr); | |||
1275 | } | |||
1276 | ||||
1277 | /* Return the mark identifier of the mark node "node". | |||
1278 | */ | |||
1279 | __isl_give isl_id *isl_ast_node_mark_get_id(__isl_keep isl_ast_node *node) | |||
1280 | { | |||
1281 | if (!node) | |||
1282 | return NULL((void*)0); | |||
1283 | if (node->type != isl_ast_node_mark) | |||
1284 | isl_die(isl_ast_node_get_ctx(node), isl_error_invalid,do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a mark node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1285); return ((void*)0); } while (0) | |||
1285 | "not a mark node", return NULL)do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a mark node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1285); return ((void*)0); } while (0); | |||
1286 | ||||
1287 | return isl_id_copy(node->u.m.mark); | |||
1288 | } | |||
1289 | ||||
1290 | /* Return the node marked by mark node "node". | |||
1291 | */ | |||
1292 | __isl_give isl_ast_node *isl_ast_node_mark_get_node( | |||
1293 | __isl_keep isl_ast_node *node) | |||
1294 | { | |||
1295 | if (!node) | |||
1296 | return NULL((void*)0); | |||
1297 | if (node->type != isl_ast_node_mark) | |||
1298 | isl_die(isl_ast_node_get_ctx(node), isl_error_invalid,do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a mark node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1299); return ((void*)0); } while (0) | |||
1299 | "not a mark node", return NULL)do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a mark node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1299); return ((void*)0); } while (0); | |||
1300 | ||||
1301 | return isl_ast_node_copy(node->u.m.node); | |||
1302 | } | |||
1303 | ||||
1304 | __isl_give isl_id *isl_ast_node_get_annotation(__isl_keep isl_ast_node *node) | |||
1305 | { | |||
1306 | return node ? isl_id_copy(node->annotation) : NULL((void*)0); | |||
1307 | } | |||
1308 | ||||
1309 | /* Replace node->annotation by "annotation". | |||
1310 | */ | |||
1311 | __isl_give isl_ast_node *isl_ast_node_set_annotation( | |||
1312 | __isl_take isl_ast_node *node, __isl_take isl_id *annotation) | |||
1313 | { | |||
1314 | node = isl_ast_node_cow(node); | |||
1315 | if (!node || !annotation) | |||
1316 | goto error; | |||
1317 | ||||
1318 | isl_id_free(node->annotation); | |||
1319 | node->annotation = annotation; | |||
1320 | ||||
1321 | return node; | |||
1322 | error: | |||
1323 | isl_id_free(annotation); | |||
1324 | return isl_ast_node_free(node); | |||
1325 | } | |||
1326 | ||||
1327 | /* Traverse the elements of "list" and all their descendants | |||
1328 | * in depth first preorder. | |||
1329 | * | |||
1330 | * Return isl_stat_ok on success and isl_stat_error on failure. | |||
1331 | */ | |||
1332 | static isl_stat nodelist_foreach(__isl_keep isl_ast_node_list *list, | |||
1333 | isl_bool (*fn)(__isl_keep isl_ast_node *node, void *user), void *user) | |||
1334 | { | |||
1335 | int i; | |||
1336 | ||||
1337 | if (!list) | |||
1338 | return isl_stat_error; | |||
1339 | ||||
1340 | for (i = 0; i < list->n; ++i) { | |||
1341 | isl_stat ok; | |||
1342 | isl_ast_node *node = list->p[i]; | |||
1343 | ||||
1344 | ok = isl_ast_node_foreach_descendant_top_down(node, fn, user); | |||
1345 | if (ok < 0) | |||
1346 | return isl_stat_error; | |||
1347 | } | |||
1348 | ||||
1349 | return isl_stat_ok; | |||
1350 | } | |||
1351 | ||||
1352 | /* Traverse the descendants of "node" (including the node itself) | |||
1353 | * in depth first preorder. | |||
1354 | * | |||
1355 | * If "fn" returns isl_bool_error on any of the nodes, then the traversal | |||
1356 | * is aborted. | |||
1357 | * If "fn" returns isl_bool_false on any of the nodes, then the subtree rooted | |||
1358 | * at that node is skipped. | |||
1359 | * | |||
1360 | * Return isl_stat_ok on success and isl_stat_error on failure. | |||
1361 | */ | |||
1362 | isl_stat isl_ast_node_foreach_descendant_top_down( | |||
1363 | __isl_keep isl_ast_node *node, | |||
1364 | isl_bool (*fn)(__isl_keep isl_ast_node *node, void *user), void *user) | |||
1365 | { | |||
1366 | isl_bool more; | |||
1367 | isl_stat ok; | |||
1368 | ||||
1369 | if (!node) | |||
1370 | return isl_stat_error; | |||
1371 | ||||
1372 | more = fn(node, user); | |||
1373 | if (more < 0) | |||
1374 | return isl_stat_error; | |||
1375 | if (!more) | |||
1376 | return isl_stat_ok; | |||
1377 | ||||
1378 | switch (node->type) { | |||
1379 | case isl_ast_node_for: | |||
1380 | node = node->u.f.body; | |||
1381 | return isl_ast_node_foreach_descendant_top_down(node, fn, user); | |||
1382 | case isl_ast_node_if: | |||
1383 | ok = isl_ast_node_foreach_descendant_top_down(node->u.i.then, | |||
1384 | fn, user); | |||
1385 | if (ok < 0) | |||
1386 | return isl_stat_error; | |||
1387 | if (!node->u.i.else_node) | |||
1388 | return isl_stat_ok; | |||
1389 | node = node->u.i.else_node; | |||
1390 | return isl_ast_node_foreach_descendant_top_down(node, fn, user); | |||
1391 | case isl_ast_node_block: | |||
1392 | return nodelist_foreach(node->u.b.children, fn, user); | |||
1393 | case isl_ast_node_mark: | |||
1394 | node = node->u.m.node; | |||
1395 | return isl_ast_node_foreach_descendant_top_down(node, fn, user); | |||
1396 | case isl_ast_node_user: | |||
1397 | break; | |||
1398 | case isl_ast_node_error: | |||
1399 | return isl_stat_error; | |||
1400 | } | |||
1401 | ||||
1402 | return isl_stat_ok; | |||
1403 | } | |||
1404 | ||||
1405 | /* Textual C representation of the various operators. | |||
1406 | */ | |||
1407 | static char *op_str_c[] = { | |||
1408 | [isl_ast_op_and] = "&&", | |||
1409 | [isl_ast_op_and_then] = "&&", | |||
1410 | [isl_ast_op_or] = "||", | |||
1411 | [isl_ast_op_or_else] = "||", | |||
1412 | [isl_ast_op_max] = "max", | |||
1413 | [isl_ast_op_min] = "min", | |||
1414 | [isl_ast_op_minus] = "-", | |||
1415 | [isl_ast_op_add] = "+", | |||
1416 | [isl_ast_op_sub] = "-", | |||
1417 | [isl_ast_op_mul] = "*", | |||
1418 | [isl_ast_op_fdiv_q] = "floord", | |||
1419 | [isl_ast_op_pdiv_q] = "/", | |||
1420 | [isl_ast_op_pdiv_r] = "%", | |||
1421 | [isl_ast_op_zdiv_r] = "%", | |||
1422 | [isl_ast_op_div] = "/", | |||
1423 | [isl_ast_op_eq] = "==", | |||
1424 | [isl_ast_op_le] = "<=", | |||
1425 | [isl_ast_op_ge] = ">=", | |||
1426 | [isl_ast_op_lt] = "<", | |||
1427 | [isl_ast_op_gt] = ">", | |||
1428 | [isl_ast_op_member] = ".", | |||
1429 | [isl_ast_op_address_of] = "&" | |||
1430 | }; | |||
1431 | ||||
1432 | /* Precedence in C of the various operators. | |||
1433 | * Based on http://en.wikipedia.org/wiki/Operators_in_C_and_C++ | |||
1434 | * Lowest value means highest precedence. | |||
1435 | */ | |||
1436 | static int op_prec[] = { | |||
1437 | [isl_ast_op_and] = 13, | |||
1438 | [isl_ast_op_and_then] = 13, | |||
1439 | [isl_ast_op_or] = 14, | |||
1440 | [isl_ast_op_or_else] = 14, | |||
1441 | [isl_ast_op_max] = 2, | |||
1442 | [isl_ast_op_min] = 2, | |||
1443 | [isl_ast_op_minus] = 3, | |||
1444 | [isl_ast_op_add] = 6, | |||
1445 | [isl_ast_op_sub] = 6, | |||
1446 | [isl_ast_op_mul] = 5, | |||
1447 | [isl_ast_op_div] = 5, | |||
1448 | [isl_ast_op_fdiv_q] = 2, | |||
1449 | [isl_ast_op_pdiv_q] = 5, | |||
1450 | [isl_ast_op_pdiv_r] = 5, | |||
1451 | [isl_ast_op_zdiv_r] = 5, | |||
1452 | [isl_ast_op_cond] = 15, | |||
1453 | [isl_ast_op_select] = 15, | |||
1454 | [isl_ast_op_eq] = 9, | |||
1455 | [isl_ast_op_le] = 8, | |||
1456 | [isl_ast_op_ge] = 8, | |||
1457 | [isl_ast_op_lt] = 8, | |||
1458 | [isl_ast_op_gt] = 8, | |||
1459 | [isl_ast_op_call] = 2, | |||
1460 | [isl_ast_op_access] = 2, | |||
1461 | [isl_ast_op_member] = 2, | |||
1462 | [isl_ast_op_address_of] = 3 | |||
1463 | }; | |||
1464 | ||||
1465 | /* Is the operator left-to-right associative? | |||
1466 | */ | |||
1467 | static int op_left[] = { | |||
1468 | [isl_ast_op_and] = 1, | |||
1469 | [isl_ast_op_and_then] = 1, | |||
1470 | [isl_ast_op_or] = 1, | |||
1471 | [isl_ast_op_or_else] = 1, | |||
1472 | [isl_ast_op_max] = 1, | |||
1473 | [isl_ast_op_min] = 1, | |||
1474 | [isl_ast_op_minus] = 0, | |||
1475 | [isl_ast_op_add] = 1, | |||
1476 | [isl_ast_op_sub] = 1, | |||
1477 | [isl_ast_op_mul] = 1, | |||
1478 | [isl_ast_op_div] = 1, | |||
1479 | [isl_ast_op_fdiv_q] = 1, | |||
1480 | [isl_ast_op_pdiv_q] = 1, | |||
1481 | [isl_ast_op_pdiv_r] = 1, | |||
1482 | [isl_ast_op_zdiv_r] = 1, | |||
1483 | [isl_ast_op_cond] = 0, | |||
1484 | [isl_ast_op_select] = 0, | |||
1485 | [isl_ast_op_eq] = 1, | |||
1486 | [isl_ast_op_le] = 1, | |||
1487 | [isl_ast_op_ge] = 1, | |||
1488 | [isl_ast_op_lt] = 1, | |||
1489 | [isl_ast_op_gt] = 1, | |||
1490 | [isl_ast_op_call] = 1, | |||
1491 | [isl_ast_op_access] = 1, | |||
1492 | [isl_ast_op_member] = 1, | |||
1493 | [isl_ast_op_address_of] = 0 | |||
1494 | }; | |||
1495 | ||||
1496 | static int is_and(enum isl_ast_op_type op) | |||
1497 | { | |||
1498 | return op == isl_ast_op_and || op == isl_ast_op_and_then; | |||
1499 | } | |||
1500 | ||||
1501 | static int is_or(enum isl_ast_op_type op) | |||
1502 | { | |||
1503 | return op == isl_ast_op_or || op == isl_ast_op_or_else; | |||
1504 | } | |||
1505 | ||||
1506 | static int is_add_sub(enum isl_ast_op_type op) | |||
1507 | { | |||
1508 | return op == isl_ast_op_add || op == isl_ast_op_sub; | |||
1509 | } | |||
1510 | ||||
1511 | static int is_div_mod(enum isl_ast_op_type op) | |||
1512 | { | |||
1513 | return op == isl_ast_op_div || | |||
1514 | op == isl_ast_op_pdiv_r || | |||
1515 | op == isl_ast_op_zdiv_r; | |||
1516 | } | |||
1517 | ||||
1518 | static __isl_give isl_printer *print_ast_expr_c(__isl_take isl_printer *p, | |||
1519 | __isl_keep isl_ast_expr *expr); | |||
1520 | ||||
1521 | /* Do we need/want parentheses around "expr" as a subexpression of | |||
1522 | * an "op" operation? If "left" is set, then "expr" is the left-most | |||
1523 | * operand. | |||
1524 | * | |||
1525 | * We only need parentheses if "expr" represents an operation. | |||
1526 | * | |||
1527 | * If op has a higher precedence than expr->u.op.op, then we need | |||
1528 | * parentheses. | |||
1529 | * If op and expr->u.op.op have the same precedence, but the operations | |||
1530 | * are performed in an order that is different from the associativity, | |||
1531 | * then we need parentheses. | |||
1532 | * | |||
1533 | * An and inside an or technically does not require parentheses, | |||
1534 | * but some compilers complain about that, so we add them anyway. | |||
1535 | * | |||
1536 | * Computations such as "a / b * c" and "a % b + c" can be somewhat | |||
1537 | * difficult to read, so we add parentheses for those as well. | |||
1538 | */ | |||
1539 | static int sub_expr_need_parens(enum isl_ast_op_type op, | |||
1540 | __isl_keep isl_ast_expr *expr, int left) | |||
1541 | { | |||
1542 | if (expr->type != isl_ast_expr_op) | |||
1543 | return 0; | |||
1544 | ||||
1545 | if (op_prec[expr->u.op.op] > op_prec[op]) | |||
1546 | return 1; | |||
1547 | if (op_prec[expr->u.op.op] == op_prec[op] && left != op_left[op]) | |||
1548 | return 1; | |||
1549 | ||||
1550 | if (is_or(op) && is_and(expr->u.op.op)) | |||
1551 | return 1; | |||
1552 | if (op == isl_ast_op_mul && expr->u.op.op != isl_ast_op_mul && | |||
1553 | op_prec[expr->u.op.op] == op_prec[op]) | |||
1554 | return 1; | |||
1555 | if (is_add_sub(op) && is_div_mod(expr->u.op.op)) | |||
1556 | return 1; | |||
1557 | ||||
1558 | return 0; | |||
1559 | } | |||
1560 | ||||
1561 | /* Print "expr" as a subexpression of an "op" operation in C format. | |||
1562 | * If "left" is set, then "expr" is the left-most operand. | |||
1563 | */ | |||
1564 | static __isl_give isl_printer *print_sub_expr_c(__isl_take isl_printer *p, | |||
1565 | enum isl_ast_op_type op, __isl_keep isl_ast_expr *expr, int left) | |||
1566 | { | |||
1567 | int need_parens; | |||
1568 | ||||
1569 | need_parens = sub_expr_need_parens(op, expr, left); | |||
1570 | ||||
1571 | if (need_parens) | |||
1572 | p = isl_printer_print_str(p, "("); | |||
1573 | p = print_ast_expr_c(p, expr); | |||
1574 | if (need_parens) | |||
1575 | p = isl_printer_print_str(p, ")"); | |||
1576 | return p; | |||
1577 | } | |||
1578 | ||||
1579 | #define isl_ast_op_lastisl_ast_op_address_of isl_ast_op_address_of | |||
1580 | ||||
1581 | /* Data structure that holds the user-specified textual | |||
1582 | * representations for the operators in C format. | |||
1583 | * The entries are either NULL or copies of strings. | |||
1584 | * A NULL entry means that the default name should be used. | |||
1585 | */ | |||
1586 | struct isl_ast_op_names { | |||
1587 | char *op_str[isl_ast_op_lastisl_ast_op_address_of + 1]; | |||
1588 | }; | |||
1589 | ||||
1590 | /* Create an empty struct isl_ast_op_names. | |||
1591 | */ | |||
1592 | static void *create_names(isl_ctx *ctx) | |||
1593 | { | |||
1594 | return isl_calloc_type(ctx, struct isl_ast_op_names)((struct isl_ast_op_names *)isl_calloc_or_die(ctx, 1, sizeof( struct isl_ast_op_names))); | |||
1595 | } | |||
1596 | ||||
1597 | /* Free a struct isl_ast_op_names along with all memory | |||
1598 | * owned by the struct. | |||
1599 | */ | |||
1600 | static void free_names(void *user) | |||
1601 | { | |||
1602 | int i; | |||
1603 | struct isl_ast_op_names *names = user; | |||
1604 | ||||
1605 | if (!user) | |||
1606 | return; | |||
1607 | ||||
1608 | for (i = 0; i <= isl_ast_op_lastisl_ast_op_address_of; ++i) | |||
1609 | free(names->op_str[i]); | |||
1610 | free(user); | |||
1611 | } | |||
1612 | ||||
1613 | /* Create an identifier that is used to store | |||
1614 | * an isl_ast_op_names note. | |||
1615 | */ | |||
1616 | static __isl_give isl_id *names_id(isl_ctx *ctx) | |||
1617 | { | |||
1618 | return isl_id_alloc(ctx, "isl_ast_op_type_names", NULL((void*)0)); | |||
1619 | } | |||
1620 | ||||
1621 | /* Ensure that "p" has a note identified by "id". | |||
1622 | * If there is no such note yet, then it is created by "note_create" and | |||
1623 | * scheduled do be freed by "note_free". | |||
1624 | */ | |||
1625 | static __isl_give isl_printer *alloc_note(__isl_take isl_printer *p, | |||
1626 | __isl_keep isl_id *id, void *(*note_create)(isl_ctx *), | |||
1627 | void (*note_free)(void *)) | |||
1628 | { | |||
1629 | isl_ctx *ctx; | |||
1630 | isl_id *note_id; | |||
1631 | isl_bool has_note; | |||
1632 | void *note; | |||
1633 | ||||
1634 | has_note = isl_printer_has_note(p, id); | |||
1635 | if (has_note < 0) | |||
1636 | return isl_printer_free(p); | |||
1637 | if (has_note) | |||
1638 | return p; | |||
1639 | ||||
1640 | ctx = isl_printer_get_ctx(p); | |||
1641 | note = note_create(ctx); | |||
1642 | if (!note) | |||
1643 | return isl_printer_free(p); | |||
1644 | note_id = isl_id_alloc(ctx, NULL((void*)0), note); | |||
1645 | if (!note_id) | |||
1646 | note_free(note); | |||
1647 | else | |||
1648 | note_id = isl_id_set_free_user(note_id, note_free); | |||
1649 | ||||
1650 | p = isl_printer_set_note(p, isl_id_copy(id), note_id); | |||
1651 | ||||
1652 | return p; | |||
1653 | } | |||
1654 | ||||
1655 | /* Ensure that "p" has an isl_ast_op_names note identified by "id". | |||
1656 | */ | |||
1657 | static __isl_give isl_printer *alloc_names(__isl_take isl_printer *p, | |||
1658 | __isl_keep isl_id *id) | |||
1659 | { | |||
1660 | return alloc_note(p, id, &create_names, &free_names); | |||
1661 | } | |||
1662 | ||||
1663 | /* Retrieve the note identified by "id" from "p". | |||
1664 | * The note is assumed to exist. | |||
1665 | */ | |||
1666 | static void *get_note(__isl_keep isl_printer *p, __isl_keep isl_id *id) | |||
1667 | { | |||
1668 | void *note; | |||
1669 | ||||
1670 | id = isl_printer_get_note(p, isl_id_copy(id)); | |||
1671 | note = isl_id_get_user(id); | |||
1672 | isl_id_free(id); | |||
1673 | ||||
1674 | return note; | |||
1675 | } | |||
1676 | ||||
1677 | /* Use "name" to print operations of type "type" to "p". | |||
1678 | * | |||
1679 | * Store the name in an isl_ast_op_names note attached to "p", such that | |||
1680 | * it can be retrieved by get_op_str. | |||
1681 | */ | |||
1682 | __isl_give isl_printer *isl_ast_op_type_set_print_name( | |||
1683 | __isl_take isl_printer *p, enum isl_ast_op_type type, | |||
1684 | __isl_keep const char *name) | |||
1685 | { | |||
1686 | isl_id *id; | |||
1687 | struct isl_ast_op_names *names; | |||
1688 | ||||
1689 | if (!p) | |||
1690 | return NULL((void*)0); | |||
1691 | if (type > isl_ast_op_lastisl_ast_op_address_of) | |||
1692 | isl_die(isl_printer_get_ctx(p), isl_error_invalid,do { isl_handle_error(isl_printer_get_ctx(p), isl_error_invalid , "invalid type", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1693); return isl_printer_free(p); } while (0) | |||
1693 | "invalid type", return isl_printer_free(p))do { isl_handle_error(isl_printer_get_ctx(p), isl_error_invalid , "invalid type", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1693); return isl_printer_free(p); } while (0); | |||
1694 | ||||
1695 | id = names_id(isl_printer_get_ctx(p)); | |||
1696 | p = alloc_names(p, id); | |||
1697 | names = get_note(p, id); | |||
1698 | isl_id_free(id); | |||
1699 | if (!names) | |||
1700 | return isl_printer_free(p); | |||
1701 | free(names->op_str[type]); | |||
1702 | names->op_str[type] = strdup(name); | |||
1703 | ||||
1704 | return p; | |||
1705 | } | |||
1706 | ||||
1707 | /* Return the textual representation of "type" in C format. | |||
1708 | * | |||
1709 | * If there is a user-specified name in an isl_ast_op_names note | |||
1710 | * associated to "p", then return that. | |||
1711 | * Otherwise, return the default name in op_str. | |||
1712 | */ | |||
1713 | static const char *get_op_str_c(__isl_keep isl_printer *p, | |||
1714 | enum isl_ast_op_type type) | |||
1715 | { | |||
1716 | isl_id *id; | |||
1717 | isl_bool has_names; | |||
1718 | struct isl_ast_op_names *names = NULL((void*)0); | |||
1719 | ||||
1720 | id = names_id(isl_printer_get_ctx(p)); | |||
1721 | has_names = isl_printer_has_note(p, id); | |||
1722 | if (has_names >= 0 && has_names) | |||
1723 | names = get_note(p, id); | |||
1724 | isl_id_free(id); | |||
1725 | if (names && names->op_str[type]) | |||
1726 | return names->op_str[type]; | |||
1727 | return op_str_c[type]; | |||
1728 | } | |||
1729 | ||||
1730 | /* Print a min or max reduction "expr" in C format. | |||
1731 | */ | |||
1732 | static __isl_give isl_printer *print_min_max_c(__isl_take isl_printer *p, | |||
1733 | __isl_keep isl_ast_expr *expr) | |||
1734 | { | |||
1735 | int i = 0; | |||
1736 | ||||
1737 | for (i = 1; i < expr->u.op.n_arg; ++i) { | |||
1738 | p = isl_printer_print_str(p, get_op_str_c(p, expr->u.op.op)); | |||
1739 | p = isl_printer_print_str(p, "("); | |||
1740 | } | |||
1741 | p = isl_printer_print_ast_expr(p, expr->u.op.args[0]); | |||
1742 | for (i = 1; i < expr->u.op.n_arg; ++i) { | |||
1743 | p = isl_printer_print_str(p, ", "); | |||
1744 | p = print_ast_expr_c(p, expr->u.op.args[i]); | |||
1745 | p = isl_printer_print_str(p, ")"); | |||
1746 | } | |||
1747 | ||||
1748 | return p; | |||
1749 | } | |||
1750 | ||||
1751 | /* Print a function call "expr" in C format. | |||
1752 | * | |||
1753 | * The first argument represents the function to be called. | |||
1754 | */ | |||
1755 | static __isl_give isl_printer *print_call_c(__isl_take isl_printer *p, | |||
1756 | __isl_keep isl_ast_expr *expr) | |||
1757 | { | |||
1758 | int i = 0; | |||
1759 | ||||
1760 | p = print_ast_expr_c(p, expr->u.op.args[0]); | |||
1761 | p = isl_printer_print_str(p, "("); | |||
1762 | for (i = 1; i < expr->u.op.n_arg; ++i) { | |||
1763 | if (i != 1) | |||
1764 | p = isl_printer_print_str(p, ", "); | |||
1765 | p = print_ast_expr_c(p, expr->u.op.args[i]); | |||
1766 | } | |||
1767 | p = isl_printer_print_str(p, ")"); | |||
1768 | ||||
1769 | return p; | |||
1770 | } | |||
1771 | ||||
1772 | /* Print an array access "expr" in C format. | |||
1773 | * | |||
1774 | * The first argument represents the array being accessed. | |||
1775 | */ | |||
1776 | static __isl_give isl_printer *print_access_c(__isl_take isl_printer *p, | |||
1777 | __isl_keep isl_ast_expr *expr) | |||
1778 | { | |||
1779 | int i = 0; | |||
1780 | ||||
1781 | p = print_ast_expr_c(p, expr->u.op.args[0]); | |||
1782 | for (i = 1; i < expr->u.op.n_arg; ++i) { | |||
1783 | p = isl_printer_print_str(p, "["); | |||
1784 | p = print_ast_expr_c(p, expr->u.op.args[i]); | |||
1785 | p = isl_printer_print_str(p, "]"); | |||
1786 | } | |||
1787 | ||||
1788 | return p; | |||
1789 | } | |||
1790 | ||||
1791 | /* Print "expr" to "p" in C format. | |||
1792 | */ | |||
1793 | static __isl_give isl_printer *print_ast_expr_c(__isl_take isl_printer *p, | |||
1794 | __isl_keep isl_ast_expr *expr) | |||
1795 | { | |||
1796 | if (!p) | |||
1797 | return NULL((void*)0); | |||
1798 | if (!expr) | |||
1799 | return isl_printer_free(p); | |||
1800 | ||||
1801 | switch (expr->type) { | |||
1802 | case isl_ast_expr_op: | |||
1803 | if (expr->u.op.op == isl_ast_op_call) { | |||
1804 | p = print_call_c(p, expr); | |||
1805 | break; | |||
1806 | } | |||
1807 | if (expr->u.op.op == isl_ast_op_access) { | |||
1808 | p = print_access_c(p, expr); | |||
1809 | break; | |||
1810 | } | |||
1811 | if (expr->u.op.n_arg == 1) { | |||
1812 | p = isl_printer_print_str(p, | |||
1813 | get_op_str_c(p, expr->u.op.op)); | |||
1814 | p = print_sub_expr_c(p, expr->u.op.op, | |||
1815 | expr->u.op.args[0], 0); | |||
1816 | break; | |||
1817 | } | |||
1818 | if (expr->u.op.op == isl_ast_op_fdiv_q) { | |||
1819 | const char *name = get_op_str_c(p, isl_ast_op_fdiv_q); | |||
1820 | p = isl_printer_print_str(p, name); | |||
1821 | p = isl_printer_print_str(p, "("); | |||
1822 | p = print_ast_expr_c(p, expr->u.op.args[0]); | |||
1823 | p = isl_printer_print_str(p, ", "); | |||
1824 | p = print_ast_expr_c(p, expr->u.op.args[1]); | |||
1825 | p = isl_printer_print_str(p, ")"); | |||
1826 | break; | |||
1827 | } | |||
1828 | if (expr->u.op.op == isl_ast_op_max || | |||
1829 | expr->u.op.op == isl_ast_op_min) { | |||
1830 | p = print_min_max_c(p, expr); | |||
1831 | break; | |||
1832 | } | |||
1833 | if (expr->u.op.op == isl_ast_op_cond || | |||
1834 | expr->u.op.op == isl_ast_op_select) { | |||
1835 | p = print_ast_expr_c(p, expr->u.op.args[0]); | |||
1836 | p = isl_printer_print_str(p, " ? "); | |||
1837 | p = print_ast_expr_c(p, expr->u.op.args[1]); | |||
1838 | p = isl_printer_print_str(p, " : "); | |||
1839 | p = print_ast_expr_c(p, expr->u.op.args[2]); | |||
1840 | break; | |||
1841 | } | |||
1842 | if (expr->u.op.n_arg != 2) | |||
1843 | isl_die(isl_printer_get_ctx(p), isl_error_internal,do { isl_handle_error(isl_printer_get_ctx(p), isl_error_internal , "operation should have two arguments", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1845); return isl_printer_free(p); } while (0) | |||
1844 | "operation should have two arguments",do { isl_handle_error(isl_printer_get_ctx(p), isl_error_internal , "operation should have two arguments", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1845); return isl_printer_free(p); } while (0) | |||
1845 | return isl_printer_free(p))do { isl_handle_error(isl_printer_get_ctx(p), isl_error_internal , "operation should have two arguments", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 1845); return isl_printer_free(p); } while (0); | |||
1846 | p = print_sub_expr_c(p, expr->u.op.op, expr->u.op.args[0], 1); | |||
1847 | if (expr->u.op.op != isl_ast_op_member) | |||
1848 | p = isl_printer_print_str(p, " "); | |||
1849 | p = isl_printer_print_str(p, get_op_str_c(p, expr->u.op.op)); | |||
1850 | if (expr->u.op.op != isl_ast_op_member) | |||
1851 | p = isl_printer_print_str(p, " "); | |||
1852 | p = print_sub_expr_c(p, expr->u.op.op, expr->u.op.args[1], 0); | |||
1853 | break; | |||
1854 | case isl_ast_expr_id: | |||
1855 | p = isl_printer_print_str(p, isl_id_get_name(expr->u.id)); | |||
1856 | break; | |||
1857 | case isl_ast_expr_int: | |||
1858 | p = isl_printer_print_val(p, expr->u.v); | |||
1859 | break; | |||
1860 | case isl_ast_expr_error: | |||
1861 | break; | |||
1862 | } | |||
1863 | ||||
1864 | return p; | |||
1865 | } | |||
1866 | ||||
1867 | /* Textual representation of the isl_ast_op_type elements | |||
1868 | * for use in a YAML representation of an isl_ast_expr. | |||
1869 | */ | |||
1870 | static char *op_str[] = { | |||
1871 | [isl_ast_op_and] = "and", | |||
1872 | [isl_ast_op_and_then] = "and_then", | |||
1873 | [isl_ast_op_or] = "or", | |||
1874 | [isl_ast_op_or_else] = "or_else", | |||
1875 | [isl_ast_op_max] = "max", | |||
1876 | [isl_ast_op_min] = "min", | |||
1877 | [isl_ast_op_minus] = "minus", | |||
1878 | [isl_ast_op_add] = "add", | |||
1879 | [isl_ast_op_sub] = "sub", | |||
1880 | [isl_ast_op_mul] = "mul", | |||
1881 | [isl_ast_op_div] = "div", | |||
1882 | [isl_ast_op_fdiv_q] = "fdiv_q", | |||
1883 | [isl_ast_op_pdiv_q] = "pdiv_q", | |||
1884 | [isl_ast_op_pdiv_r] = "pdiv_r", | |||
1885 | [isl_ast_op_zdiv_r] = "zdiv_r", | |||
1886 | [isl_ast_op_cond] = "cond", | |||
1887 | [isl_ast_op_select] = "select", | |||
1888 | [isl_ast_op_eq] = "eq", | |||
1889 | [isl_ast_op_le] = "le", | |||
1890 | [isl_ast_op_lt] = "lt", | |||
1891 | [isl_ast_op_ge] = "ge", | |||
1892 | [isl_ast_op_gt] = "gt", | |||
1893 | [isl_ast_op_call] = "call", | |||
1894 | [isl_ast_op_access] = "access", | |||
1895 | [isl_ast_op_member] = "member", | |||
1896 | [isl_ast_op_address_of] = "address_of" | |||
1897 | }; | |||
1898 | ||||
1899 | static __isl_give isl_printer *print_ast_expr_isl(__isl_take isl_printer *p, | |||
1900 | __isl_keep isl_ast_expr *expr); | |||
1901 | ||||
1902 | /* Print the arguments of "expr" to "p" in isl format. | |||
1903 | * | |||
1904 | * If there are no arguments, then nothing needs to be printed. | |||
1905 | * Otherwise add an "args" key to the current mapping with as value | |||
1906 | * the list of arguments of "expr". | |||
1907 | */ | |||
1908 | static __isl_give isl_printer *print_arguments(__isl_take isl_printer *p, | |||
1909 | __isl_keep isl_ast_expr *expr) | |||
1910 | { | |||
1911 | int i, n; | |||
1912 | ||||
1913 | n = isl_ast_expr_get_op_n_arg(expr); | |||
1914 | if (n < 0) | |||
1915 | return isl_printer_free(p); | |||
1916 | if (n == 0) | |||
1917 | return p; | |||
1918 | ||||
1919 | p = isl_printer_print_str(p, "args"); | |||
1920 | p = isl_printer_yaml_next(p); | |||
1921 | p = isl_printer_yaml_start_sequence(p); | |||
1922 | for (i = 0; i < n; ++i) { | |||
1923 | isl_ast_expr *arg; | |||
1924 | ||||
1925 | arg = isl_ast_expr_get_op_arg(expr, i); | |||
1926 | p = print_ast_expr_isl(p, arg); | |||
1927 | isl_ast_expr_free(arg); | |||
1928 | p = isl_printer_yaml_next(p); | |||
1929 | } | |||
1930 | p = isl_printer_yaml_end_sequence(p); | |||
1931 | ||||
1932 | return p; | |||
1933 | } | |||
1934 | ||||
1935 | /* Print "expr" to "p" in isl format. | |||
1936 | * | |||
1937 | * In particular, print the isl_ast_expr as a YAML document. | |||
1938 | */ | |||
1939 | static __isl_give isl_printer *print_ast_expr_isl(__isl_take isl_printer *p, | |||
1940 | __isl_keep isl_ast_expr *expr) | |||
1941 | { | |||
1942 | enum isl_ast_expr_type type; | |||
1943 | enum isl_ast_op_type op; | |||
1944 | isl_id *id; | |||
1945 | isl_val *v; | |||
1946 | ||||
1947 | if (!expr) | |||
1948 | return isl_printer_free(p); | |||
1949 | ||||
1950 | p = isl_printer_yaml_start_mapping(p); | |||
1951 | type = isl_ast_expr_get_type(expr); | |||
1952 | switch (type) { | |||
1953 | case isl_ast_expr_error: | |||
1954 | return isl_printer_free(p); | |||
1955 | case isl_ast_expr_op: | |||
1956 | op = isl_ast_expr_get_op_type(expr); | |||
1957 | if (op == isl_ast_op_error) | |||
1958 | return isl_printer_free(p); | |||
1959 | p = isl_printer_print_str(p, "op"); | |||
1960 | p = isl_printer_yaml_next(p); | |||
1961 | p = isl_printer_print_str(p, op_str[op]); | |||
1962 | p = isl_printer_yaml_next(p); | |||
1963 | p = print_arguments(p, expr); | |||
1964 | break; | |||
1965 | case isl_ast_expr_id: | |||
1966 | p = isl_printer_print_str(p, "id"); | |||
1967 | p = isl_printer_yaml_next(p); | |||
1968 | id = isl_ast_expr_get_id(expr); | |||
1969 | p = isl_printer_print_id(p, id); | |||
1970 | isl_id_free(id); | |||
1971 | break; | |||
1972 | case isl_ast_expr_int: | |||
1973 | p = isl_printer_print_str(p, "val"); | |||
1974 | p = isl_printer_yaml_next(p); | |||
1975 | v = isl_ast_expr_get_val(expr); | |||
1976 | p = isl_printer_print_val(p, v); | |||
1977 | isl_val_free(v); | |||
1978 | break; | |||
1979 | } | |||
1980 | p = isl_printer_yaml_end_mapping(p); | |||
1981 | ||||
1982 | return p; | |||
1983 | } | |||
1984 | ||||
1985 | /* Print "expr" to "p". | |||
1986 | * | |||
1987 | * Only an isl and a C format are supported. | |||
1988 | */ | |||
1989 | __isl_give isl_printer *isl_printer_print_ast_expr(__isl_take isl_printer *p, | |||
1990 | __isl_keep isl_ast_expr *expr) | |||
1991 | { | |||
1992 | int format; | |||
1993 | ||||
1994 | if (!p) | |||
1995 | return NULL((void*)0); | |||
1996 | ||||
1997 | format = isl_printer_get_output_format(p); | |||
1998 | switch (format) { | |||
1999 | case ISL_FORMAT_ISL0: | |||
2000 | p = print_ast_expr_isl(p, expr); | |||
2001 | break; | |||
2002 | case ISL_FORMAT_C4: | |||
2003 | p = print_ast_expr_c(p, expr); | |||
2004 | break; | |||
2005 | default: | |||
2006 | isl_die(isl_printer_get_ctx(p), isl_error_unsupported,do { isl_handle_error(isl_printer_get_ctx(p), isl_error_unsupported , "output format not supported for ast_expr", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 2008); return isl_printer_free(p); } while (0) | |||
2007 | "output format not supported for ast_expr",do { isl_handle_error(isl_printer_get_ctx(p), isl_error_unsupported , "output format not supported for ast_expr", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 2008); return isl_printer_free(p); } while (0) | |||
2008 | return isl_printer_free(p))do { isl_handle_error(isl_printer_get_ctx(p), isl_error_unsupported , "output format not supported for ast_expr", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 2008); return isl_printer_free(p); } while (0); | |||
2009 | } | |||
2010 | ||||
2011 | return p; | |||
2012 | } | |||
2013 | ||||
2014 | static __isl_give isl_printer *print_ast_node_isl(__isl_take isl_printer *p, | |||
2015 | __isl_keep isl_ast_node *node); | |||
2016 | ||||
2017 | /* Print a YAML sequence containing the entries in "list" to "p". | |||
2018 | */ | |||
2019 | static __isl_give isl_printer *print_ast_node_list(__isl_take isl_printer *p, | |||
2020 | __isl_keep isl_ast_node_list *list) | |||
2021 | { | |||
2022 | int i, n; | |||
2023 | ||||
2024 | n = isl_ast_node_list_n_ast_node(list); | |||
2025 | if (n < 0) | |||
2026 | return isl_printer_free(p); | |||
2027 | ||||
2028 | p = isl_printer_yaml_start_sequence(p); | |||
2029 | for (i = 0; i < n; ++i) { | |||
2030 | isl_ast_node *node; | |||
2031 | ||||
2032 | node = isl_ast_node_list_get_ast_node(list, i); | |||
2033 | p = print_ast_node_isl(p, node); | |||
2034 | isl_ast_node_free(node); | |||
2035 | p = isl_printer_yaml_next(p); | |||
2036 | } | |||
2037 | p = isl_printer_yaml_end_sequence(p); | |||
2038 | ||||
2039 | return p; | |||
2040 | } | |||
2041 | ||||
2042 | /* Print "node" to "p" in "isl format". | |||
2043 | * | |||
2044 | * In particular, print the isl_ast_node as a YAML document. | |||
2045 | */ | |||
2046 | static __isl_give isl_printer *print_ast_node_isl(__isl_take isl_printer *p, | |||
2047 | __isl_keep isl_ast_node *node) | |||
2048 | { | |||
2049 | switch (node->type) { | |||
2050 | case isl_ast_node_for: | |||
2051 | p = isl_printer_yaml_start_mapping(p); | |||
2052 | p = isl_printer_print_str(p, "iterator"); | |||
2053 | p = isl_printer_yaml_next(p); | |||
2054 | p = isl_printer_print_ast_expr(p, node->u.f.iterator); | |||
2055 | p = isl_printer_yaml_next(p); | |||
2056 | if (node->u.f.degenerate) { | |||
2057 | p = isl_printer_print_str(p, "value"); | |||
2058 | p = isl_printer_yaml_next(p); | |||
2059 | p = isl_printer_print_ast_expr(p, node->u.f.init); | |||
2060 | p = isl_printer_yaml_next(p); | |||
2061 | } else { | |||
2062 | p = isl_printer_print_str(p, "init"); | |||
2063 | p = isl_printer_yaml_next(p); | |||
2064 | p = isl_printer_print_ast_expr(p, node->u.f.init); | |||
2065 | p = isl_printer_yaml_next(p); | |||
2066 | p = isl_printer_print_str(p, "cond"); | |||
2067 | p = isl_printer_yaml_next(p); | |||
2068 | p = isl_printer_print_ast_expr(p, node->u.f.cond); | |||
2069 | p = isl_printer_yaml_next(p); | |||
2070 | p = isl_printer_print_str(p, "inc"); | |||
2071 | p = isl_printer_yaml_next(p); | |||
2072 | p = isl_printer_print_ast_expr(p, node->u.f.inc); | |||
2073 | p = isl_printer_yaml_next(p); | |||
2074 | } | |||
2075 | if (node->u.f.body) { | |||
2076 | p = isl_printer_print_str(p, "body"); | |||
2077 | p = isl_printer_yaml_next(p); | |||
2078 | p = isl_printer_print_ast_node(p, node->u.f.body); | |||
2079 | p = isl_printer_yaml_next(p); | |||
2080 | } | |||
2081 | p = isl_printer_yaml_end_mapping(p); | |||
2082 | break; | |||
2083 | case isl_ast_node_mark: | |||
2084 | p = isl_printer_yaml_start_mapping(p); | |||
2085 | p = isl_printer_print_str(p, "mark"); | |||
2086 | p = isl_printer_yaml_next(p); | |||
2087 | p = isl_printer_print_id(p, node->u.m.mark); | |||
2088 | p = isl_printer_yaml_next(p); | |||
2089 | p = isl_printer_print_str(p, "node"); | |||
2090 | p = isl_printer_yaml_next(p); | |||
2091 | p = isl_printer_print_ast_node(p, node->u.m.node); | |||
2092 | p = isl_printer_yaml_end_mapping(p); | |||
2093 | break; | |||
2094 | case isl_ast_node_user: | |||
2095 | p = isl_printer_yaml_start_mapping(p); | |||
2096 | p = isl_printer_print_str(p, "user"); | |||
2097 | p = isl_printer_yaml_next(p); | |||
2098 | p = isl_printer_print_ast_expr(p, node->u.e.expr); | |||
2099 | p = isl_printer_yaml_end_mapping(p); | |||
2100 | break; | |||
2101 | case isl_ast_node_if: | |||
2102 | p = isl_printer_yaml_start_mapping(p); | |||
2103 | p = isl_printer_print_str(p, "guard"); | |||
2104 | p = isl_printer_yaml_next(p); | |||
2105 | p = isl_printer_print_ast_expr(p, node->u.i.guard); | |||
2106 | p = isl_printer_yaml_next(p); | |||
2107 | if (node->u.i.then) { | |||
2108 | p = isl_printer_print_str(p, "then"); | |||
2109 | p = isl_printer_yaml_next(p); | |||
2110 | p = isl_printer_print_ast_node(p, node->u.i.then); | |||
2111 | p = isl_printer_yaml_next(p); | |||
2112 | } | |||
2113 | if (node->u.i.else_node) { | |||
2114 | p = isl_printer_print_str(p, "else"); | |||
2115 | p = isl_printer_yaml_next(p); | |||
2116 | p = isl_printer_print_ast_node(p, node->u.i.else_node); | |||
2117 | } | |||
2118 | p = isl_printer_yaml_end_mapping(p); | |||
2119 | break; | |||
2120 | case isl_ast_node_block: | |||
2121 | p = print_ast_node_list(p, node->u.b.children); | |||
2122 | break; | |||
2123 | case isl_ast_node_error: | |||
2124 | break; | |||
2125 | } | |||
2126 | return p; | |||
2127 | } | |||
2128 | ||||
2129 | /* Do we need to print a block around the body "node" of a for or if node? | |||
2130 | * | |||
2131 | * If the node is a block, then we need to print a block. | |||
2132 | * Also if the node is a degenerate for then we will print it as | |||
2133 | * an assignment followed by the body of the for loop, so we need a block | |||
2134 | * as well. | |||
2135 | * If the node is an if node with an else, then we print a block | |||
2136 | * to avoid spurious dangling else warnings emitted by some compilers. | |||
2137 | * If the node is a mark, then in principle, we would have to check | |||
2138 | * the child of the mark node. However, even if the child would not | |||
2139 | * require us to print a block, for readability it is probably best | |||
2140 | * to print a block anyway. | |||
2141 | * If the ast_always_print_block option has been set, then we print a block. | |||
2142 | */ | |||
2143 | static int need_block(__isl_keep isl_ast_node *node) | |||
2144 | { | |||
2145 | isl_ctx *ctx; | |||
2146 | ||||
2147 | if (node->type == isl_ast_node_block) | |||
2148 | return 1; | |||
2149 | if (node->type == isl_ast_node_for && node->u.f.degenerate) | |||
2150 | return 1; | |||
2151 | if (node->type == isl_ast_node_if && node->u.i.else_node) | |||
2152 | return 1; | |||
2153 | if (node->type == isl_ast_node_mark) | |||
2154 | return 1; | |||
2155 | ||||
2156 | ctx = isl_ast_node_get_ctx(node); | |||
2157 | return isl_options_get_ast_always_print_block(ctx); | |||
2158 | } | |||
2159 | ||||
2160 | static __isl_give isl_printer *print_ast_node_c(__isl_take isl_printer *p, | |||
2161 | __isl_keep isl_ast_node *node, | |||
2162 | __isl_keep isl_ast_print_options *options, int in_block, int in_list); | |||
2163 | static __isl_give isl_printer *print_if_c(__isl_take isl_printer *p, | |||
2164 | __isl_keep isl_ast_node *node, | |||
2165 | __isl_keep isl_ast_print_options *options, int new_line, | |||
2166 | int force_block); | |||
2167 | ||||
2168 | /* Print the body "node" of a for or if node. | |||
2169 | * If "else_node" is set, then it is printed as well. | |||
2170 | * If "force_block" is set, then print out the body as a block. | |||
2171 | * | |||
2172 | * We first check if we need to print out a block. | |||
2173 | * We always print out a block if there is an else node to make | |||
2174 | * sure that the else node is matched to the correct if node. | |||
2175 | * For consistency, the corresponding else node is also printed as a block. | |||
2176 | * | |||
2177 | * If the else node is itself an if, then we print it as | |||
2178 | * | |||
2179 | * } else if (..) { | |||
2180 | * } | |||
2181 | * | |||
2182 | * Otherwise the else node is printed as | |||
2183 | * | |||
2184 | * } else { | |||
2185 | * node | |||
2186 | * } | |||
2187 | */ | |||
2188 | static __isl_give isl_printer *print_body_c(__isl_take isl_printer *p, | |||
2189 | __isl_keep isl_ast_node *node, __isl_keep isl_ast_node *else_node, | |||
2190 | __isl_keep isl_ast_print_options *options, int force_block) | |||
2191 | { | |||
2192 | if (!node) | |||
2193 | return isl_printer_free(p); | |||
2194 | ||||
2195 | if (!force_block && !else_node && !need_block(node)) { | |||
2196 | p = isl_printer_end_line(p); | |||
2197 | p = isl_printer_indent(p, 2); | |||
2198 | p = isl_ast_node_print(node, p, | |||
2199 | isl_ast_print_options_copy(options)); | |||
2200 | p = isl_printer_indent(p, -2); | |||
2201 | return p; | |||
2202 | } | |||
2203 | ||||
2204 | p = isl_printer_print_str(p, " {"); | |||
2205 | p = isl_printer_end_line(p); | |||
2206 | p = isl_printer_indent(p, 2); | |||
2207 | p = print_ast_node_c(p, node, options, 1, 0); | |||
2208 | p = isl_printer_indent(p, -2); | |||
2209 | p = isl_printer_start_line(p); | |||
2210 | p = isl_printer_print_str(p, "}"); | |||
2211 | if (else_node) { | |||
2212 | if (else_node->type == isl_ast_node_if) { | |||
2213 | p = isl_printer_print_str(p, " else "); | |||
2214 | p = print_if_c(p, else_node, options, 0, 1); | |||
2215 | } else { | |||
2216 | p = isl_printer_print_str(p, " else"); | |||
2217 | p = print_body_c(p, else_node, NULL((void*)0), options, 1); | |||
2218 | } | |||
2219 | } else | |||
2220 | p = isl_printer_end_line(p); | |||
2221 | ||||
2222 | return p; | |||
2223 | } | |||
2224 | ||||
2225 | /* Print the start of a compound statement. | |||
2226 | */ | |||
2227 | static __isl_give isl_printer *start_block(__isl_take isl_printer *p) | |||
2228 | { | |||
2229 | p = isl_printer_start_line(p); | |||
2230 | p = isl_printer_print_str(p, "{"); | |||
2231 | p = isl_printer_end_line(p); | |||
2232 | p = isl_printer_indent(p, 2); | |||
2233 | ||||
2234 | return p; | |||
2235 | } | |||
2236 | ||||
2237 | /* Print the end of a compound statement. | |||
2238 | */ | |||
2239 | static __isl_give isl_printer *end_block(__isl_take isl_printer *p) | |||
2240 | { | |||
2241 | p = isl_printer_indent(p, -2); | |||
2242 | p = isl_printer_start_line(p); | |||
2243 | p = isl_printer_print_str(p, "}"); | |||
2244 | p = isl_printer_end_line(p); | |||
2245 | ||||
2246 | return p; | |||
2247 | } | |||
2248 | ||||
2249 | /* Print the for node "node". | |||
2250 | * | |||
2251 | * If the for node is degenerate, it is printed as | |||
2252 | * | |||
2253 | * type iterator = init; | |||
2254 | * body | |||
2255 | * | |||
2256 | * Otherwise, it is printed as | |||
2257 | * | |||
2258 | * for (type iterator = init; cond; iterator += inc) | |||
2259 | * body | |||
2260 | * | |||
2261 | * "in_block" is set if we are currently inside a block. | |||
2262 | * "in_list" is set if the current node is not alone in the block. | |||
2263 | * If we are not in a block or if the current not is not alone in the block | |||
2264 | * then we print a block around a degenerate for loop such that the variable | |||
2265 | * declaration will not conflict with any potential other declaration | |||
2266 | * of the same variable. | |||
2267 | */ | |||
2268 | static __isl_give isl_printer *print_for_c(__isl_take isl_printer *p, | |||
2269 | __isl_keep isl_ast_node *node, | |||
2270 | __isl_keep isl_ast_print_options *options, int in_block, int in_list) | |||
2271 | { | |||
2272 | isl_id *id; | |||
2273 | const char *name; | |||
2274 | const char *type; | |||
2275 | ||||
2276 | type = isl_options_get_ast_iterator_type(isl_printer_get_ctx(p)); | |||
2277 | if (!node->u.f.degenerate) { | |||
2278 | id = isl_ast_expr_get_id(node->u.f.iterator); | |||
2279 | name = isl_id_get_name(id); | |||
2280 | isl_id_free(id); | |||
2281 | p = isl_printer_start_line(p); | |||
2282 | p = isl_printer_print_str(p, "for ("); | |||
2283 | p = isl_printer_print_str(p, type); | |||
2284 | p = isl_printer_print_str(p, " "); | |||
2285 | p = isl_printer_print_str(p, name); | |||
2286 | p = isl_printer_print_str(p, " = "); | |||
2287 | p = isl_printer_print_ast_expr(p, node->u.f.init); | |||
2288 | p = isl_printer_print_str(p, "; "); | |||
2289 | p = isl_printer_print_ast_expr(p, node->u.f.cond); | |||
2290 | p = isl_printer_print_str(p, "; "); | |||
2291 | p = isl_printer_print_str(p, name); | |||
2292 | p = isl_printer_print_str(p, " += "); | |||
2293 | p = isl_printer_print_ast_expr(p, node->u.f.inc); | |||
2294 | p = isl_printer_print_str(p, ")"); | |||
2295 | p = print_body_c(p, node->u.f.body, NULL((void*)0), options, 0); | |||
2296 | } else { | |||
2297 | id = isl_ast_expr_get_id(node->u.f.iterator); | |||
2298 | name = isl_id_get_name(id); | |||
2299 | isl_id_free(id); | |||
2300 | if (!in_block || in_list) | |||
2301 | p = start_block(p); | |||
2302 | p = isl_printer_start_line(p); | |||
2303 | p = isl_printer_print_str(p, type); | |||
2304 | p = isl_printer_print_str(p, " "); | |||
2305 | p = isl_printer_print_str(p, name); | |||
2306 | p = isl_printer_print_str(p, " = "); | |||
2307 | p = isl_printer_print_ast_expr(p, node->u.f.init); | |||
2308 | p = isl_printer_print_str(p, ";"); | |||
2309 | p = isl_printer_end_line(p); | |||
2310 | p = print_ast_node_c(p, node->u.f.body, options, 1, 0); | |||
2311 | if (!in_block || in_list) | |||
2312 | p = end_block(p); | |||
2313 | } | |||
2314 | ||||
2315 | return p; | |||
2316 | } | |||
2317 | ||||
2318 | /* Print the if node "node". | |||
2319 | * If "new_line" is set then the if node should be printed on a new line. | |||
2320 | * If "force_block" is set, then print out the body as a block. | |||
2321 | */ | |||
2322 | static __isl_give isl_printer *print_if_c(__isl_take isl_printer *p, | |||
2323 | __isl_keep isl_ast_node *node, | |||
2324 | __isl_keep isl_ast_print_options *options, int new_line, | |||
2325 | int force_block) | |||
2326 | { | |||
2327 | if (new_line) | |||
2328 | p = isl_printer_start_line(p); | |||
2329 | p = isl_printer_print_str(p, "if ("); | |||
2330 | p = isl_printer_print_ast_expr(p, node->u.i.guard); | |||
2331 | p = isl_printer_print_str(p, ")"); | |||
2332 | p = print_body_c(p, node->u.i.then, node->u.i.else_node, options, | |||
2333 | force_block); | |||
2334 | ||||
2335 | return p; | |||
2336 | } | |||
2337 | ||||
2338 | /* Print the "node" to "p". | |||
2339 | * | |||
2340 | * "in_block" is set if we are currently inside a block. | |||
2341 | * If so, we do not print a block around the children of a block node. | |||
2342 | * We do this to avoid an extra block around the body of a degenerate | |||
2343 | * for node. | |||
2344 | * | |||
2345 | * "in_list" is set if the current node is not alone in the block. | |||
2346 | */ | |||
2347 | static __isl_give isl_printer *print_ast_node_c(__isl_take isl_printer *p, | |||
2348 | __isl_keep isl_ast_node *node, | |||
2349 | __isl_keep isl_ast_print_options *options, int in_block, int in_list) | |||
2350 | { | |||
2351 | switch (node->type) { | |||
2352 | case isl_ast_node_for: | |||
2353 | if (options->print_for) | |||
2354 | return options->print_for(p, | |||
2355 | isl_ast_print_options_copy(options), | |||
2356 | node, options->print_for_user); | |||
2357 | p = print_for_c(p, node, options, in_block, in_list); | |||
2358 | break; | |||
2359 | case isl_ast_node_if: | |||
2360 | p = print_if_c(p, node, options, 1, 0); | |||
2361 | break; | |||
2362 | case isl_ast_node_block: | |||
2363 | if (!in_block) | |||
2364 | p = start_block(p); | |||
2365 | p = isl_ast_node_list_print(node->u.b.children, p, options); | |||
2366 | if (!in_block) | |||
2367 | p = end_block(p); | |||
2368 | break; | |||
2369 | case isl_ast_node_mark: | |||
2370 | p = isl_printer_start_line(p); | |||
2371 | p = isl_printer_print_str(p, "// "); | |||
2372 | p = isl_printer_print_str(p, isl_id_get_name(node->u.m.mark)); | |||
2373 | p = isl_printer_end_line(p); | |||
2374 | p = print_ast_node_c(p, node->u.m.node, options, 0, in_list); | |||
2375 | break; | |||
2376 | case isl_ast_node_user: | |||
2377 | if (options->print_user) | |||
2378 | return options->print_user(p, | |||
2379 | isl_ast_print_options_copy(options), | |||
2380 | node, options->print_user_user); | |||
2381 | p = isl_printer_start_line(p); | |||
2382 | p = isl_printer_print_ast_expr(p, node->u.e.expr); | |||
2383 | p = isl_printer_print_str(p, ";"); | |||
2384 | p = isl_printer_end_line(p); | |||
2385 | break; | |||
2386 | case isl_ast_node_error: | |||
2387 | break; | |||
2388 | } | |||
2389 | return p; | |||
2390 | } | |||
2391 | ||||
2392 | /* Print the for node "node" to "p". | |||
2393 | */ | |||
2394 | __isl_give isl_printer *isl_ast_node_for_print(__isl_keep isl_ast_node *node, | |||
2395 | __isl_take isl_printer *p, __isl_take isl_ast_print_options *options) | |||
2396 | { | |||
2397 | if (!node || !options) | |||
| ||||
2398 | goto error; | |||
2399 | if (node->type != isl_ast_node_for) | |||
2400 | isl_die(isl_ast_node_get_ctx(node), isl_error_invalid,do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a for node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 2401); goto error; } while (0) | |||
2401 | "not a for node", goto error)do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not a for node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 2401); goto error; } while (0); | |||
2402 | p = print_for_c(p, node, options, 0, 0); | |||
2403 | isl_ast_print_options_free(options); | |||
| ||||
2404 | return p; | |||
2405 | error: | |||
2406 | isl_ast_print_options_free(options); | |||
2407 | isl_printer_free(p); | |||
2408 | return NULL((void*)0); | |||
2409 | } | |||
2410 | ||||
2411 | /* Print the if node "node" to "p". | |||
2412 | */ | |||
2413 | __isl_give isl_printer *isl_ast_node_if_print(__isl_keep isl_ast_node *node, | |||
2414 | __isl_take isl_printer *p, __isl_take isl_ast_print_options *options) | |||
2415 | { | |||
2416 | if (!node || !options) | |||
2417 | goto error; | |||
2418 | if (node->type != isl_ast_node_if) | |||
2419 | isl_die(isl_ast_node_get_ctx(node), isl_error_invalid,do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not an if node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 2420); goto error; } while (0) | |||
2420 | "not an if node", goto error)do { isl_handle_error(isl_ast_node_get_ctx(node), isl_error_invalid , "not an if node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 2420); goto error; } while (0); | |||
2421 | p = print_if_c(p, node, options, 1, 0); | |||
2422 | isl_ast_print_options_free(options); | |||
2423 | return p; | |||
2424 | error: | |||
2425 | isl_ast_print_options_free(options); | |||
2426 | isl_printer_free(p); | |||
2427 | return NULL((void*)0); | |||
2428 | } | |||
2429 | ||||
2430 | /* Print "node" to "p". | |||
2431 | */ | |||
2432 | __isl_give isl_printer *isl_ast_node_print(__isl_keep isl_ast_node *node, | |||
2433 | __isl_take isl_printer *p, __isl_take isl_ast_print_options *options) | |||
2434 | { | |||
2435 | if (!options || !node) | |||
2436 | goto error; | |||
2437 | p = print_ast_node_c(p, node, options, 0, 0); | |||
2438 | isl_ast_print_options_free(options); | |||
2439 | return p; | |||
2440 | error: | |||
2441 | isl_ast_print_options_free(options); | |||
2442 | isl_printer_free(p); | |||
2443 | return NULL((void*)0); | |||
2444 | } | |||
2445 | ||||
2446 | /* Print "node" to "p". | |||
2447 | */ | |||
2448 | __isl_give isl_printer *isl_printer_print_ast_node(__isl_take isl_printer *p, | |||
2449 | __isl_keep isl_ast_node *node) | |||
2450 | { | |||
2451 | int format; | |||
2452 | isl_ast_print_options *options; | |||
2453 | ||||
2454 | if (!p) | |||
2455 | return NULL((void*)0); | |||
2456 | ||||
2457 | format = isl_printer_get_output_format(p); | |||
2458 | switch (format) { | |||
2459 | case ISL_FORMAT_ISL0: | |||
2460 | p = print_ast_node_isl(p, node); | |||
2461 | break; | |||
2462 | case ISL_FORMAT_C4: | |||
2463 | options = isl_ast_print_options_alloc(isl_printer_get_ctx(p)); | |||
2464 | p = isl_ast_node_print(node, p, options); | |||
2465 | break; | |||
2466 | default: | |||
2467 | isl_die(isl_printer_get_ctx(p), isl_error_unsupported,do { isl_handle_error(isl_printer_get_ctx(p), isl_error_unsupported , "output format not supported for ast_node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 2469); return isl_printer_free(p); } while (0) | |||
2468 | "output format not supported for ast_node",do { isl_handle_error(isl_printer_get_ctx(p), isl_error_unsupported , "output format not supported for ast_node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 2469); return isl_printer_free(p); } while (0) | |||
2469 | return isl_printer_free(p))do { isl_handle_error(isl_printer_get_ctx(p), isl_error_unsupported , "output format not supported for ast_node", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 2469); return isl_printer_free(p); } while (0); | |||
2470 | } | |||
2471 | ||||
2472 | return p; | |||
2473 | } | |||
2474 | ||||
2475 | /* Print the list of nodes "list" to "p". | |||
2476 | */ | |||
2477 | __isl_give isl_printer *isl_ast_node_list_print( | |||
2478 | __isl_keep isl_ast_node_list *list, __isl_take isl_printer *p, | |||
2479 | __isl_keep isl_ast_print_options *options) | |||
2480 | { | |||
2481 | int i; | |||
2482 | ||||
2483 | if (!p || !list || !options) | |||
2484 | return isl_printer_free(p); | |||
2485 | ||||
2486 | for (i = 0; i < list->n; ++i) | |||
2487 | p = print_ast_node_c(p, list->p[i], options, 1, 1); | |||
2488 | ||||
2489 | return p; | |||
2490 | } | |||
2491 | ||||
2492 | #define ISL_AST_MACRO_FLOORD(1 << 0) (1 << 0) | |||
2493 | #define ISL_AST_MACRO_MIN(1 << 1) (1 << 1) | |||
2494 | #define ISL_AST_MACRO_MAX(1 << 2) (1 << 2) | |||
2495 | #define ISL_AST_MACRO_ALL((1 << 0) | (1 << 1) | (1 << 2)) (ISL_AST_MACRO_FLOORD(1 << 0) | \ | |||
2496 | ISL_AST_MACRO_MIN(1 << 1) | \ | |||
2497 | ISL_AST_MACRO_MAX(1 << 2)) | |||
2498 | ||||
2499 | /* If "expr" contains an isl_ast_op_min, isl_ast_op_max or isl_ast_op_fdiv_q | |||
2500 | * then set the corresponding bit in "macros". | |||
2501 | */ | |||
2502 | static int ast_expr_required_macros(__isl_keep isl_ast_expr *expr, int macros) | |||
2503 | { | |||
2504 | int i; | |||
2505 | ||||
2506 | if (macros == ISL_AST_MACRO_ALL((1 << 0) | (1 << 1) | (1 << 2))) | |||
2507 | return macros; | |||
2508 | ||||
2509 | if (expr->type != isl_ast_expr_op) | |||
2510 | return macros; | |||
2511 | ||||
2512 | if (expr->u.op.op == isl_ast_op_min) | |||
2513 | macros |= ISL_AST_MACRO_MIN(1 << 1); | |||
2514 | if (expr->u.op.op == isl_ast_op_max) | |||
2515 | macros |= ISL_AST_MACRO_MAX(1 << 2); | |||
2516 | if (expr->u.op.op == isl_ast_op_fdiv_q) | |||
2517 | macros |= ISL_AST_MACRO_FLOORD(1 << 0); | |||
2518 | ||||
2519 | for (i = 0; i < expr->u.op.n_arg; ++i) | |||
2520 | macros = ast_expr_required_macros(expr->u.op.args[i], macros); | |||
2521 | ||||
2522 | return macros; | |||
2523 | } | |||
2524 | ||||
2525 | static int ast_node_list_required_macros(__isl_keep isl_ast_node_list *list, | |||
2526 | int macros); | |||
2527 | ||||
2528 | /* If "node" contains an isl_ast_op_min, isl_ast_op_max or isl_ast_op_fdiv_q | |||
2529 | * then set the corresponding bit in "macros". | |||
2530 | */ | |||
2531 | static int ast_node_required_macros(__isl_keep isl_ast_node *node, int macros) | |||
2532 | { | |||
2533 | if (macros == ISL_AST_MACRO_ALL((1 << 0) | (1 << 1) | (1 << 2))) | |||
2534 | return macros; | |||
2535 | ||||
2536 | switch (node->type) { | |||
2537 | case isl_ast_node_for: | |||
2538 | macros = ast_expr_required_macros(node->u.f.init, macros); | |||
2539 | if (!node->u.f.degenerate) { | |||
2540 | macros = ast_expr_required_macros(node->u.f.cond, | |||
2541 | macros); | |||
2542 | macros = ast_expr_required_macros(node->u.f.inc, | |||
2543 | macros); | |||
2544 | } | |||
2545 | macros = ast_node_required_macros(node->u.f.body, macros); | |||
2546 | break; | |||
2547 | case isl_ast_node_if: | |||
2548 | macros = ast_expr_required_macros(node->u.i.guard, macros); | |||
2549 | macros = ast_node_required_macros(node->u.i.then, macros); | |||
2550 | if (node->u.i.else_node) | |||
2551 | macros = ast_node_required_macros(node->u.i.else_node, | |||
2552 | macros); | |||
2553 | break; | |||
2554 | case isl_ast_node_block: | |||
2555 | macros = ast_node_list_required_macros(node->u.b.children, | |||
2556 | macros); | |||
2557 | break; | |||
2558 | case isl_ast_node_mark: | |||
2559 | macros = ast_node_required_macros(node->u.m.node, macros); | |||
2560 | break; | |||
2561 | case isl_ast_node_user: | |||
2562 | macros = ast_expr_required_macros(node->u.e.expr, macros); | |||
2563 | break; | |||
2564 | case isl_ast_node_error: | |||
2565 | break; | |||
2566 | } | |||
2567 | ||||
2568 | return macros; | |||
2569 | } | |||
2570 | ||||
2571 | /* If "list" contains an isl_ast_op_min, isl_ast_op_max or isl_ast_op_fdiv_q | |||
2572 | * then set the corresponding bit in "macros". | |||
2573 | */ | |||
2574 | static int ast_node_list_required_macros(__isl_keep isl_ast_node_list *list, | |||
2575 | int macros) | |||
2576 | { | |||
2577 | int i; | |||
2578 | ||||
2579 | for (i = 0; i < list->n; ++i) | |||
2580 | macros = ast_node_required_macros(list->p[i], macros); | |||
2581 | ||||
2582 | return macros; | |||
2583 | } | |||
2584 | ||||
2585 | /* Data structure for keeping track of whether a macro definition | |||
2586 | * for a given type has already been printed. | |||
2587 | * The value is zero if no definition has been printed and non-zero otherwise. | |||
2588 | */ | |||
2589 | struct isl_ast_op_printed { | |||
2590 | char printed[isl_ast_op_lastisl_ast_op_address_of + 1]; | |||
2591 | }; | |||
2592 | ||||
2593 | /* Create an empty struct isl_ast_op_printed. | |||
2594 | */ | |||
2595 | static void *create_printed(isl_ctx *ctx) | |||
2596 | { | |||
2597 | return isl_calloc_type(ctx, struct isl_ast_op_printed)((struct isl_ast_op_printed *)isl_calloc_or_die(ctx, 1, sizeof (struct isl_ast_op_printed))); | |||
2598 | } | |||
2599 | ||||
2600 | /* Free a struct isl_ast_op_printed. | |||
2601 | */ | |||
2602 | static void free_printed(void *user) | |||
2603 | { | |||
2604 | free(user); | |||
2605 | } | |||
2606 | ||||
2607 | /* Ensure that "p" has an isl_ast_op_printed note identified by "id". | |||
2608 | */ | |||
2609 | static __isl_give isl_printer *alloc_printed(__isl_take isl_printer *p, | |||
2610 | __isl_keep isl_id *id) | |||
2611 | { | |||
2612 | return alloc_note(p, id, &create_printed, &free_printed); | |||
2613 | } | |||
2614 | ||||
2615 | /* Create an identifier that is used to store | |||
2616 | * an isl_ast_op_printed note. | |||
2617 | */ | |||
2618 | static __isl_give isl_id *printed_id(isl_ctx *ctx) | |||
2619 | { | |||
2620 | return isl_id_alloc(ctx, "isl_ast_op_type_printed", NULL((void*)0)); | |||
2621 | } | |||
2622 | ||||
2623 | /* Did the user specify that a macro definition should only be | |||
2624 | * printed once and has a macro definition for "type" already | |||
2625 | * been printed to "p"? | |||
2626 | * If definitions should only be printed once, but a definition | |||
2627 | * for "p" has not yet been printed, then mark it as having been | |||
2628 | * printed so that it will not printed again. | |||
2629 | * The actual printing is taken care of by the caller. | |||
2630 | */ | |||
2631 | static isl_bool already_printed_once(__isl_keep isl_printer *p, | |||
2632 | enum isl_ast_op_type type) | |||
2633 | { | |||
2634 | isl_ctx *ctx; | |||
2635 | isl_id *id; | |||
2636 | struct isl_ast_op_printed *printed; | |||
2637 | ||||
2638 | if (!p) | |||
2639 | return isl_bool_error; | |||
2640 | ||||
2641 | ctx = isl_printer_get_ctx(p); | |||
2642 | if (!isl_options_get_ast_print_macro_once(ctx)) | |||
2643 | return isl_bool_false; | |||
2644 | ||||
2645 | if (type > isl_ast_op_lastisl_ast_op_address_of) | |||
2646 | isl_die(isl_printer_get_ctx(p), isl_error_invalid,do { isl_handle_error(isl_printer_get_ctx(p), isl_error_invalid , "invalid type", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 2647); return isl_bool_error; } while (0) | |||
2647 | "invalid type", return isl_bool_error)do { isl_handle_error(isl_printer_get_ctx(p), isl_error_invalid , "invalid type", "/build/llvm-toolchain-snapshot-7~svn329677/tools/polly/lib/External/isl/isl_ast.c" , 2647); return isl_bool_error; } while (0); | |||
2648 | ||||
2649 | id = printed_id(isl_printer_get_ctx(p)); | |||
2650 | p = alloc_printed(p, id); | |||
2651 | printed = get_note(p, id); | |||
2652 | isl_id_free(id); | |||
2653 | if (!printed) | |||
2654 | return isl_bool_error; | |||
2655 | ||||
2656 | if (printed->printed[type]) | |||
2657 | return isl_bool_true; | |||
2658 | ||||
2659 | printed->printed[type] = 1; | |||
2660 | return isl_bool_false; | |||
2661 | } | |||
2662 | ||||
2663 | /* Print a macro definition for the operator "type". | |||
2664 | * | |||
2665 | * If the user has specified that a macro definition should | |||
2666 | * only be printed once to any given printer and if the macro definition | |||
2667 | * has already been printed to "p", then do not print the definition. | |||
2668 | */ | |||
2669 | __isl_give isl_printer *isl_ast_op_type_print_macro( | |||
2670 | enum isl_ast_op_type type, __isl_take isl_printer *p) | |||
2671 | { | |||
2672 | isl_bool skip; | |||
2673 | ||||
2674 | skip = already_printed_once(p, type); | |||
2675 | if (skip < 0) | |||
2676 | return isl_printer_free(p); | |||
2677 | if (skip) | |||
2678 | return p; | |||
2679 | ||||
2680 | switch (type) { | |||
2681 | case isl_ast_op_min: | |||
2682 | p = isl_printer_start_line(p); | |||
2683 | p = isl_printer_print_str(p, "#define "); | |||
2684 | p = isl_printer_print_str(p, get_op_str_c(p, type)); | |||
2685 | p = isl_printer_print_str(p, | |||
2686 | "(x,y) ((x) < (y) ? (x) : (y))"); | |||
2687 | p = isl_printer_end_line(p); | |||
2688 | break; | |||
2689 | case isl_ast_op_max: | |||
2690 | p = isl_printer_start_line(p); | |||
2691 | p = isl_printer_print_str(p, "#define "); | |||
2692 | p = isl_printer_print_str(p, get_op_str_c(p, type)); | |||
2693 | p = isl_printer_print_str(p, | |||
2694 | "(x,y) ((x) > (y) ? (x) : (y))"); | |||
2695 | p = isl_printer_end_line(p); | |||
2696 | break; | |||
2697 | case isl_ast_op_fdiv_q: | |||
2698 | p = isl_printer_start_line(p); | |||
2699 | p = isl_printer_print_str(p, "#define "); | |||
2700 | p = isl_printer_print_str(p, get_op_str_c(p, type)); | |||
2701 | p = isl_printer_print_str(p, | |||
2702 | "(n,d) " | |||
2703 | "(((n)<0) ? -((-(n)+(d)-1)/(d)) : (n)/(d))"); | |||
2704 | p = isl_printer_end_line(p); | |||
2705 | break; | |||
2706 | default: | |||
2707 | break; | |||
2708 | } | |||
2709 | ||||
2710 | return p; | |||
2711 | } | |||
2712 | ||||
2713 | /* Call "fn" for each type of operation represented in the "macros" | |||
2714 | * bit vector. | |||
2715 | */ | |||
2716 | static isl_stat foreach_ast_op_type(int macros, | |||
2717 | isl_stat (*fn)(enum isl_ast_op_type type, void *user), void *user) | |||
2718 | { | |||
2719 | if (macros & ISL_AST_MACRO_MIN(1 << 1) && fn(isl_ast_op_min, user) < 0) | |||
2720 | return isl_stat_error; | |||
2721 | if (macros & ISL_AST_MACRO_MAX(1 << 2) && fn(isl_ast_op_max, user) < 0) | |||
2722 | return isl_stat_error; | |||
2723 | if (macros & ISL_AST_MACRO_FLOORD(1 << 0) && fn(isl_ast_op_fdiv_q, user) < 0) | |||
2724 | return isl_stat_error; | |||
2725 | ||||
2726 | return isl_stat_ok; | |||
2727 | } | |||
2728 | ||||
2729 | /* Call "fn" for each type of operation that appears in "expr" | |||
2730 | * and that requires a macro definition. | |||
2731 | */ | |||
2732 | isl_stat isl_ast_expr_foreach_ast_op_type(__isl_keep isl_ast_expr *expr, | |||
2733 | isl_stat (*fn)(enum isl_ast_op_type type, void *user), void *user) | |||
2734 | { | |||
2735 | int macros; | |||
2736 | ||||
2737 | if (!expr) | |||
2738 | return isl_stat_error; | |||
2739 | ||||
2740 | macros = ast_expr_required_macros(expr, 0); | |||
2741 | return foreach_ast_op_type(macros, fn, user); | |||
2742 | } | |||
2743 | ||||
2744 | /* Call "fn" for each type of operation that appears in "node" | |||
2745 | * and that requires a macro definition. | |||
2746 | */ | |||
2747 | isl_stat isl_ast_node_foreach_ast_op_type(__isl_keep isl_ast_node *node, | |||
2748 | isl_stat (*fn)(enum isl_ast_op_type type, void *user), void *user) | |||
2749 | { | |||
2750 | int macros; | |||
2751 | ||||
2752 | if (!node) | |||
2753 | return isl_stat_error; | |||
2754 | ||||
2755 | macros = ast_node_required_macros(node, 0); | |||
2756 | return foreach_ast_op_type(macros, fn, user); | |||
2757 | } | |||
2758 | ||||
2759 | static isl_stat ast_op_type_print_macro(enum isl_ast_op_type type, void *user) | |||
2760 | { | |||
2761 | isl_printer **p = user; | |||
2762 | ||||
2763 | *p = isl_ast_op_type_print_macro(type, *p); | |||
2764 | ||||
2765 | return isl_stat_ok; | |||
2766 | } | |||
2767 | ||||
2768 | /* Print macro definitions for all the macros used in the result | |||
2769 | * of printing "expr". | |||
2770 | */ | |||
2771 | __isl_give isl_printer *isl_ast_expr_print_macros( | |||
2772 | __isl_keep isl_ast_expr *expr, __isl_take isl_printer *p) | |||
2773 | { | |||
2774 | if (isl_ast_expr_foreach_ast_op_type(expr, | |||
2775 | &ast_op_type_print_macro, &p) < 0) | |||
2776 | return isl_printer_free(p); | |||
2777 | return p; | |||
2778 | } | |||
2779 | ||||
2780 | /* Print macro definitions for all the macros used in the result | |||
2781 | * of printing "node". | |||
2782 | */ | |||
2783 | __isl_give isl_printer *isl_ast_node_print_macros( | |||
2784 | __isl_keep isl_ast_node *node, __isl_take isl_printer *p) | |||
2785 | { | |||
2786 | if (isl_ast_node_foreach_ast_op_type(node, | |||
2787 | &ast_op_type_print_macro, &p) < 0) | |||
2788 | return isl_printer_free(p); | |||
2789 | return p; | |||
2790 | } | |||
2791 | ||||
2792 | /* Return a string containing C code representing this isl_ast_expr. | |||
2793 | */ | |||
2794 | __isl_give char *isl_ast_expr_to_C_str(__isl_keep isl_ast_expr *expr) | |||
2795 | { | |||
2796 | isl_printer *p; | |||
2797 | char *str; | |||
2798 | ||||
2799 | if (!expr) | |||
2800 | return NULL((void*)0); | |||
2801 | ||||
2802 | p = isl_printer_to_str(isl_ast_expr_get_ctx(expr)); | |||
2803 | p = isl_printer_set_output_format(p, ISL_FORMAT_C4); | |||
2804 | p = isl_printer_print_ast_expr(p, expr); | |||
2805 | ||||
2806 | str = isl_printer_get_str(p); | |||
2807 | ||||
2808 | isl_printer_free(p); | |||
2809 | ||||
2810 | return str; | |||
2811 | } | |||
2812 | ||||
2813 | /* Return a string containing C code representing this isl_ast_node. | |||
2814 | */ | |||
2815 | __isl_give char *isl_ast_node_to_C_str(__isl_keep isl_ast_node *node) | |||
2816 | { | |||
2817 | isl_printer *p; | |||
2818 | char *str; | |||
2819 | ||||
2820 | if (!node) | |||
2821 | return NULL((void*)0); | |||
2822 | ||||
2823 | p = isl_printer_to_str(isl_ast_node_get_ctx(node)); | |||
2824 | p = isl_printer_set_output_format(p, ISL_FORMAT_C4); | |||
2825 | p = isl_printer_print_ast_node(p, node); | |||
2826 | ||||
2827 | str = isl_printer_get_str(p); | |||
2828 | ||||
2829 | isl_printer_free(p); | |||
2830 | ||||
2831 | return str; | |||
2832 | } |