1 #include <isl_ast_private.h>
2 #include <isl/val_int.h>
7 #include <isl_list_templ.c>
12 #include <isl_list_templ.c>
14 isl_ctx
*isl_ast_print_options_get_ctx(
15 __isl_keep isl_ast_print_options
*options
)
17 return options
? options
->ctx
: NULL
;
20 __isl_give isl_ast_print_options
*isl_ast_print_options_alloc(isl_ctx
*ctx
)
22 isl_ast_print_options
*options
;
24 options
= isl_calloc_type(ctx
, isl_ast_print_options
);
35 __isl_give isl_ast_print_options
*isl_ast_print_options_dup(
36 __isl_keep isl_ast_print_options
*options
)
39 isl_ast_print_options
*dup
;
44 ctx
= isl_ast_print_options_get_ctx(options
);
45 dup
= isl_ast_print_options_alloc(ctx
);
49 dup
->print_for
= options
->print_for
;
50 dup
->print_for_user
= options
->print_for_user
;
51 dup
->print_user
= options
->print_user
;
52 dup
->print_user_user
= options
->print_user_user
;
57 __isl_give isl_ast_print_options
*isl_ast_print_options_cow(
58 __isl_take isl_ast_print_options
*options
)
63 if (options
->ref
== 1)
66 return isl_ast_print_options_dup(options
);
69 __isl_give isl_ast_print_options
*isl_ast_print_options_copy(
70 __isl_keep isl_ast_print_options
*options
)
79 void *isl_ast_print_options_free(__isl_take isl_ast_print_options
*options
)
84 if (--options
->ref
> 0)
87 isl_ctx_deref(options
->ctx
);
93 /* Set the print_user callback of "options" to "print_user".
95 * If this callback is set, then it used to print user nodes in the AST.
96 * Otherwise, the expression associated to the user node is printed.
98 __isl_give isl_ast_print_options
*isl_ast_print_options_set_print_user(
99 __isl_take isl_ast_print_options
*options
,
100 __isl_give isl_printer
*(*print_user
)(__isl_take isl_printer
*p
,
101 __isl_take isl_ast_print_options
*options
,
102 __isl_keep isl_ast_node
*node
, void *user
),
105 options
= isl_ast_print_options_cow(options
);
109 options
->print_user
= print_user
;
110 options
->print_user_user
= user
;
115 /* Set the print_for callback of "options" to "print_for".
117 * If this callback is set, then it used to print for nodes in the AST.
119 __isl_give isl_ast_print_options
*isl_ast_print_options_set_print_for(
120 __isl_take isl_ast_print_options
*options
,
121 __isl_give isl_printer
*(*print_for
)(__isl_take isl_printer
*p
,
122 __isl_take isl_ast_print_options
*options
,
123 __isl_keep isl_ast_node
*node
, void *user
),
126 options
= isl_ast_print_options_cow(options
);
130 options
->print_for
= print_for
;
131 options
->print_for_user
= user
;
136 __isl_give isl_ast_expr
*isl_ast_expr_copy(__isl_keep isl_ast_expr
*expr
)
145 __isl_give isl_ast_expr
*isl_ast_expr_dup(__isl_keep isl_ast_expr
*expr
)
154 ctx
= isl_ast_expr_get_ctx(expr
);
155 switch (expr
->type
) {
156 case isl_ast_expr_int
:
157 dup
= isl_ast_expr_alloc_int(ctx
, expr
->u
.i
);
159 case isl_ast_expr_id
:
160 dup
= isl_ast_expr_from_id(isl_id_copy(expr
->u
.id
));
162 case isl_ast_expr_op
:
163 dup
= isl_ast_expr_alloc_op(ctx
,
164 expr
->u
.op
.op
, expr
->u
.op
.n_arg
);
167 for (i
= 0; i
< expr
->u
.op
.n_arg
; ++i
)
169 isl_ast_expr_copy(expr
->u
.op
.args
[i
]);
171 case isl_ast_expr_error
:
181 __isl_give isl_ast_expr
*isl_ast_expr_cow(__isl_take isl_ast_expr
*expr
)
189 return isl_ast_expr_dup(expr
);
192 void *isl_ast_expr_free(__isl_take isl_ast_expr
*expr
)
202 isl_ctx_deref(expr
->ctx
);
204 switch (expr
->type
) {
205 case isl_ast_expr_int
:
206 isl_int_clear(expr
->u
.i
);
208 case isl_ast_expr_id
:
209 isl_id_free(expr
->u
.id
);
211 case isl_ast_expr_op
:
212 for (i
= 0; i
< expr
->u
.op
.n_arg
; ++i
)
213 isl_ast_expr_free(expr
->u
.op
.args
[i
]);
214 free(expr
->u
.op
.args
);
216 case isl_ast_expr_error
:
224 isl_ctx
*isl_ast_expr_get_ctx(__isl_keep isl_ast_expr
*expr
)
226 return expr
? expr
->ctx
: NULL
;
229 enum isl_ast_expr_type
isl_ast_expr_get_type(__isl_keep isl_ast_expr
*expr
)
231 return expr
? expr
->type
: isl_ast_expr_error
;
234 int isl_ast_expr_get_int(__isl_keep isl_ast_expr
*expr
, isl_int
*v
)
238 if (expr
->type
!= isl_ast_expr_int
)
239 isl_die(isl_ast_expr_get_ctx(expr
), isl_error_invalid
,
240 "expression not an int", return -1);
241 isl_int_set(*v
, expr
->u
.i
);
245 /* Return the integer value represented by "expr".
247 __isl_give isl_val
*isl_ast_expr_get_val(__isl_keep isl_ast_expr
*expr
)
253 ctx
= isl_ast_expr_get_ctx(expr
);
254 if (expr
->type
!= isl_ast_expr_int
)
255 isl_die(ctx
, isl_error_invalid
,
256 "expression not an int", return NULL
);
257 return isl_val_int_from_isl_int(ctx
, expr
->u
.i
);
260 __isl_give isl_id
*isl_ast_expr_get_id(__isl_keep isl_ast_expr
*expr
)
264 if (expr
->type
!= isl_ast_expr_id
)
265 isl_die(isl_ast_expr_get_ctx(expr
), isl_error_invalid
,
266 "expression not an identifier", return NULL
);
268 return isl_id_copy(expr
->u
.id
);
271 enum isl_ast_op_type
isl_ast_expr_get_op_type(__isl_keep isl_ast_expr
*expr
)
274 return isl_ast_op_error
;
275 if (expr
->type
!= isl_ast_expr_op
)
276 isl_die(isl_ast_expr_get_ctx(expr
), isl_error_invalid
,
277 "expression not an operation", return isl_ast_op_error
);
278 return expr
->u
.op
.op
;
281 int isl_ast_expr_get_op_n_arg(__isl_keep isl_ast_expr
*expr
)
285 if (expr
->type
!= isl_ast_expr_op
)
286 isl_die(isl_ast_expr_get_ctx(expr
), isl_error_invalid
,
287 "expression not an operation", return -1);
288 return expr
->u
.op
.n_arg
;
291 __isl_give isl_ast_expr
*isl_ast_expr_get_op_arg(__isl_keep isl_ast_expr
*expr
,
296 if (expr
->type
!= isl_ast_expr_op
)
297 isl_die(isl_ast_expr_get_ctx(expr
), isl_error_invalid
,
298 "expression not an operation", return NULL
);
299 if (pos
< 0 || pos
>= expr
->u
.op
.n_arg
)
300 isl_die(isl_ast_expr_get_ctx(expr
), isl_error_invalid
,
301 "index out of bounds", return NULL
);
303 return isl_ast_expr_copy(expr
->u
.op
.args
[pos
]);
306 /* Replace the argument at position "pos" of "expr" by "arg".
308 __isl_give isl_ast_expr
*isl_ast_expr_set_op_arg(__isl_take isl_ast_expr
*expr
,
309 int pos
, __isl_take isl_ast_expr
*arg
)
311 expr
= isl_ast_expr_cow(expr
);
314 if (expr
->type
!= isl_ast_expr_op
)
315 isl_die(isl_ast_expr_get_ctx(expr
), isl_error_invalid
,
316 "expression not an operation", goto error
);
317 if (pos
< 0 || pos
>= expr
->u
.op
.n_arg
)
318 isl_die(isl_ast_expr_get_ctx(expr
), isl_error_invalid
,
319 "index out of bounds", goto error
);
321 isl_ast_expr_free(expr
->u
.op
.args
[pos
]);
322 expr
->u
.op
.args
[pos
] = arg
;
326 isl_ast_expr_free(arg
);
327 return isl_ast_expr_free(expr
);
330 /* Create a new operation expression of operation type "op",
331 * with "n_arg" as yet unspecified arguments.
333 __isl_give isl_ast_expr
*isl_ast_expr_alloc_op(isl_ctx
*ctx
,
334 enum isl_ast_op_type op
, int n_arg
)
338 expr
= isl_calloc_type(ctx
, isl_ast_expr
);
345 expr
->type
= isl_ast_expr_op
;
347 expr
->u
.op
.n_arg
= n_arg
;
348 expr
->u
.op
.args
= isl_calloc_array(ctx
, isl_ast_expr
*, n_arg
);
350 if (!expr
->u
.op
.args
)
351 return isl_ast_expr_free(expr
);
356 /* Create a new id expression representing "id".
358 __isl_give isl_ast_expr
*isl_ast_expr_from_id(__isl_take isl_id
*id
)
366 ctx
= isl_id_get_ctx(id
);
367 expr
= isl_calloc_type(ctx
, isl_ast_expr
);
369 return isl_id_free(id
);
374 expr
->type
= isl_ast_expr_id
;
380 /* Create a new integer expression representing "i".
382 __isl_give isl_ast_expr
*isl_ast_expr_alloc_int_si(isl_ctx
*ctx
, int i
)
386 expr
= isl_calloc_type(ctx
, isl_ast_expr
);
393 expr
->type
= isl_ast_expr_int
;
395 isl_int_init(expr
->u
.i
);
396 isl_int_set_si(expr
->u
.i
, i
);
401 /* Create a new integer expression representing "i".
403 __isl_give isl_ast_expr
*isl_ast_expr_alloc_int(isl_ctx
*ctx
, isl_int i
)
407 expr
= isl_calloc_type(ctx
, isl_ast_expr
);
414 expr
->type
= isl_ast_expr_int
;
416 isl_int_init(expr
->u
.i
);
417 isl_int_set(expr
->u
.i
, i
);
422 /* Create a new integer expression representing "v".
424 __isl_give isl_ast_expr
*isl_ast_expr_from_val(__isl_take isl_val
*v
)
431 if (!isl_val_is_int(v
))
432 isl_die(isl_val_get_ctx(v
), isl_error_invalid
,
433 "expecting integer value", return isl_val_free(v
));
435 ctx
= isl_val_get_ctx(v
);
436 expr
= isl_calloc_type(ctx
, isl_ast_expr
);
438 return isl_val_free(v
);
443 expr
->type
= isl_ast_expr_int
;
445 isl_int_init(expr
->u
.i
);
446 isl_int_set(expr
->u
.i
, v
->n
);
452 /* Create an expression representing the negation of "arg".
454 __isl_give isl_ast_expr
*isl_ast_expr_neg(__isl_take isl_ast_expr
*arg
)
457 isl_ast_expr
*expr
= NULL
;
462 ctx
= isl_ast_expr_get_ctx(arg
);
463 expr
= isl_ast_expr_alloc_op(ctx
, isl_ast_op_minus
, 1);
467 expr
->u
.op
.args
[0] = arg
;
471 isl_ast_expr_free(arg
);
475 /* Create an expression representing the binary operation "type"
476 * applied to "expr1" and "expr2".
478 __isl_give isl_ast_expr
*isl_ast_expr_alloc_binary(enum isl_ast_op_type type
,
479 __isl_take isl_ast_expr
*expr1
, __isl_take isl_ast_expr
*expr2
)
482 isl_ast_expr
*expr
= NULL
;
484 if (!expr1
|| !expr2
)
487 ctx
= isl_ast_expr_get_ctx(expr1
);
488 expr
= isl_ast_expr_alloc_op(ctx
, type
, 2);
492 expr
->u
.op
.args
[0] = expr1
;
493 expr
->u
.op
.args
[1] = expr2
;
497 isl_ast_expr_free(expr1
);
498 isl_ast_expr_free(expr2
);
502 /* Create an expression representing the sum of "expr1" and "expr2".
504 __isl_give isl_ast_expr
*isl_ast_expr_add(__isl_take isl_ast_expr
*expr1
,
505 __isl_take isl_ast_expr
*expr2
)
507 return isl_ast_expr_alloc_binary(isl_ast_op_add
, expr1
, expr2
);
510 /* Create an expression representing the difference of "expr1" and "expr2".
512 __isl_give isl_ast_expr
*isl_ast_expr_sub(__isl_take isl_ast_expr
*expr1
,
513 __isl_take isl_ast_expr
*expr2
)
515 return isl_ast_expr_alloc_binary(isl_ast_op_sub
, expr1
, expr2
);
518 /* Create an expression representing the product of "expr1" and "expr2".
520 __isl_give isl_ast_expr
*isl_ast_expr_mul(__isl_take isl_ast_expr
*expr1
,
521 __isl_take isl_ast_expr
*expr2
)
523 return isl_ast_expr_alloc_binary(isl_ast_op_mul
, expr1
, expr2
);
526 /* Create an expression representing the quotient of "expr1" and "expr2".
528 __isl_give isl_ast_expr
*isl_ast_expr_div(__isl_take isl_ast_expr
*expr1
,
529 __isl_take isl_ast_expr
*expr2
)
531 return isl_ast_expr_alloc_binary(isl_ast_op_div
, expr1
, expr2
);
534 /* Create an expression representing the conjunction of "expr1" and "expr2".
536 __isl_give isl_ast_expr
*isl_ast_expr_and(__isl_take isl_ast_expr
*expr1
,
537 __isl_take isl_ast_expr
*expr2
)
539 return isl_ast_expr_alloc_binary(isl_ast_op_and
, expr1
, expr2
);
542 /* Create an expression representing the disjunction of "expr1" and "expr2".
544 __isl_give isl_ast_expr
*isl_ast_expr_or(__isl_take isl_ast_expr
*expr1
,
545 __isl_take isl_ast_expr
*expr2
)
547 return isl_ast_expr_alloc_binary(isl_ast_op_or
, expr1
, expr2
);
550 isl_ctx
*isl_ast_node_get_ctx(__isl_keep isl_ast_node
*node
)
552 return node
? node
->ctx
: NULL
;
555 enum isl_ast_node_type
isl_ast_node_get_type(__isl_keep isl_ast_node
*node
)
557 return node
? node
->type
: isl_ast_node_error
;
560 __isl_give isl_ast_node
*isl_ast_node_alloc(isl_ctx
*ctx
,
561 enum isl_ast_node_type type
)
565 node
= isl_calloc_type(ctx
, isl_ast_node
);
577 /* Create an if node with the given guard.
579 * The then body needs to be filled in later.
581 __isl_give isl_ast_node
*isl_ast_node_alloc_if(__isl_take isl_ast_expr
*guard
)
588 node
= isl_ast_node_alloc(isl_ast_expr_get_ctx(guard
), isl_ast_node_if
);
591 node
->u
.i
.guard
= guard
;
595 isl_ast_expr_free(guard
);
599 /* Create a for node with the given iterator.
601 * The remaining fields need to be filled in later.
603 __isl_give isl_ast_node
*isl_ast_node_alloc_for(__isl_take isl_id
*id
)
611 ctx
= isl_id_get_ctx(id
);
612 node
= isl_ast_node_alloc(ctx
, isl_ast_node_for
);
616 node
->u
.f
.iterator
= isl_ast_expr_from_id(id
);
617 if (!node
->u
.f
.iterator
)
618 return isl_ast_node_free(node
);
623 /* Create a user node evaluating "expr".
625 __isl_give isl_ast_node
*isl_ast_node_alloc_user(__isl_take isl_ast_expr
*expr
)
633 ctx
= isl_ast_expr_get_ctx(expr
);
634 node
= isl_ast_node_alloc(ctx
, isl_ast_node_user
);
638 node
->u
.e
.expr
= expr
;
642 isl_ast_expr_free(expr
);
646 /* Create a block node with the given children.
648 __isl_give isl_ast_node
*isl_ast_node_alloc_block(
649 __isl_take isl_ast_node_list
*list
)
657 ctx
= isl_ast_node_list_get_ctx(list
);
658 node
= isl_ast_node_alloc(ctx
, isl_ast_node_block
);
662 node
->u
.b
.children
= list
;
666 isl_ast_node_list_free(list
);
670 /* Represent the given list of nodes as a single node, either by
671 * extract the node from a single element list or by creating
672 * a block node with the list of nodes as children.
674 __isl_give isl_ast_node
*isl_ast_node_from_ast_node_list(
675 __isl_take isl_ast_node_list
*list
)
679 if (isl_ast_node_list_n_ast_node(list
) != 1)
680 return isl_ast_node_alloc_block(list
);
682 node
= isl_ast_node_list_get_ast_node(list
, 0);
683 isl_ast_node_list_free(list
);
688 __isl_give isl_ast_node
*isl_ast_node_copy(__isl_keep isl_ast_node
*node
)
697 __isl_give isl_ast_node
*isl_ast_node_dup(__isl_keep isl_ast_node
*node
)
704 dup
= isl_ast_node_alloc(isl_ast_node_get_ctx(node
), node
->type
);
708 switch (node
->type
) {
709 case isl_ast_node_if
:
710 dup
->u
.i
.guard
= isl_ast_expr_copy(node
->u
.i
.guard
);
711 dup
->u
.i
.then
= isl_ast_node_copy(node
->u
.i
.then
);
712 dup
->u
.i
.else_node
= isl_ast_node_copy(node
->u
.i
.else_node
);
713 if (!dup
->u
.i
.guard
|| !dup
->u
.i
.then
||
714 (node
->u
.i
.else_node
&& !dup
->u
.i
.else_node
))
715 return isl_ast_node_free(dup
);
717 case isl_ast_node_for
:
718 dup
->u
.f
.iterator
= isl_ast_expr_copy(node
->u
.f
.iterator
);
719 dup
->u
.f
.init
= isl_ast_expr_copy(node
->u
.f
.init
);
720 dup
->u
.f
.cond
= isl_ast_expr_copy(node
->u
.f
.cond
);
721 dup
->u
.f
.inc
= isl_ast_expr_copy(node
->u
.f
.inc
);
722 dup
->u
.f
.body
= isl_ast_node_copy(node
->u
.f
.body
);
723 if (!dup
->u
.f
.iterator
|| !dup
->u
.f
.init
|| !dup
->u
.f
.cond
||
724 !dup
->u
.f
.inc
|| !dup
->u
.f
.body
)
725 return isl_ast_node_free(dup
);
727 case isl_ast_node_block
:
728 dup
->u
.b
.children
= isl_ast_node_list_copy(node
->u
.b
.children
);
729 if (!dup
->u
.b
.children
)
730 return isl_ast_node_free(dup
);
732 case isl_ast_node_user
:
733 dup
->u
.e
.expr
= isl_ast_expr_copy(node
->u
.e
.expr
);
735 return isl_ast_node_free(dup
);
737 case isl_ast_node_error
:
744 __isl_give isl_ast_node
*isl_ast_node_cow(__isl_take isl_ast_node
*node
)
752 return isl_ast_node_dup(node
);
755 void *isl_ast_node_free(__isl_take isl_ast_node
*node
)
763 switch (node
->type
) {
764 case isl_ast_node_if
:
765 isl_ast_expr_free(node
->u
.i
.guard
);
766 isl_ast_node_free(node
->u
.i
.then
);
767 isl_ast_node_free(node
->u
.i
.else_node
);
769 case isl_ast_node_for
:
770 isl_ast_expr_free(node
->u
.f
.iterator
);
771 isl_ast_expr_free(node
->u
.f
.init
);
772 isl_ast_expr_free(node
->u
.f
.cond
);
773 isl_ast_expr_free(node
->u
.f
.inc
);
774 isl_ast_node_free(node
->u
.f
.body
);
776 case isl_ast_node_block
:
777 isl_ast_node_list_free(node
->u
.b
.children
);
779 case isl_ast_node_user
:
780 isl_ast_expr_free(node
->u
.e
.expr
);
782 case isl_ast_node_error
:
786 isl_id_free(node
->annotation
);
787 isl_ctx_deref(node
->ctx
);
793 /* Replace the body of the for node "node" by "body".
795 __isl_give isl_ast_node
*isl_ast_node_for_set_body(
796 __isl_take isl_ast_node
*node
, __isl_take isl_ast_node
*body
)
798 node
= isl_ast_node_cow(node
);
801 if (node
->type
!= isl_ast_node_for
)
802 isl_die(isl_ast_node_get_ctx(node
), isl_error_invalid
,
803 "not a for node", goto error
);
805 isl_ast_node_free(node
->u
.f
.body
);
806 node
->u
.f
.body
= body
;
810 isl_ast_node_free(node
);
811 isl_ast_node_free(body
);
815 __isl_give isl_ast_node
*isl_ast_node_for_get_body(
816 __isl_keep isl_ast_node
*node
)
820 if (node
->type
!= isl_ast_node_for
)
821 isl_die(isl_ast_node_get_ctx(node
), isl_error_invalid
,
822 "not a for node", return NULL
);
823 return isl_ast_node_copy(node
->u
.f
.body
);
826 /* Mark the given for node as being degenerate.
828 __isl_give isl_ast_node
*isl_ast_node_for_mark_degenerate(
829 __isl_take isl_ast_node
*node
)
831 node
= isl_ast_node_cow(node
);
834 node
->u
.f
.degenerate
= 1;
838 int isl_ast_node_for_is_degenerate(__isl_keep isl_ast_node
*node
)
842 if (node
->type
!= isl_ast_node_for
)
843 isl_die(isl_ast_node_get_ctx(node
), isl_error_invalid
,
844 "not a for node", return -1);
845 return node
->u
.f
.degenerate
;
848 __isl_give isl_ast_expr
*isl_ast_node_for_get_iterator(
849 __isl_keep isl_ast_node
*node
)
853 if (node
->type
!= isl_ast_node_for
)
854 isl_die(isl_ast_node_get_ctx(node
), isl_error_invalid
,
855 "not a for node", return NULL
);
856 return isl_ast_expr_copy(node
->u
.f
.iterator
);
859 __isl_give isl_ast_expr
*isl_ast_node_for_get_init(
860 __isl_keep isl_ast_node
*node
)
864 if (node
->type
!= isl_ast_node_for
)
865 isl_die(isl_ast_node_get_ctx(node
), isl_error_invalid
,
866 "not a for node", return NULL
);
867 return isl_ast_expr_copy(node
->u
.f
.init
);
870 /* Return the condition expression of the given for node.
872 * If the for node is degenerate, then the condition is not explicitly
873 * stored in the node. Instead, it is constructed as
877 __isl_give isl_ast_expr
*isl_ast_node_for_get_cond(
878 __isl_keep isl_ast_node
*node
)
882 if (node
->type
!= isl_ast_node_for
)
883 isl_die(isl_ast_node_get_ctx(node
), isl_error_invalid
,
884 "not a for node", return NULL
);
885 if (!node
->u
.f
.degenerate
)
886 return isl_ast_expr_copy(node
->u
.f
.cond
);
888 return isl_ast_expr_alloc_binary(isl_ast_op_le
,
889 isl_ast_expr_copy(node
->u
.f
.iterator
),
890 isl_ast_expr_copy(node
->u
.f
.init
));
893 /* Return the increment of the given for node.
895 * If the for node is degenerate, then the increment is not explicitly
896 * stored in the node. We simply return "1".
898 __isl_give isl_ast_expr
*isl_ast_node_for_get_inc(
899 __isl_keep isl_ast_node
*node
)
903 if (node
->type
!= isl_ast_node_for
)
904 isl_die(isl_ast_node_get_ctx(node
), isl_error_invalid
,
905 "not a for node", return NULL
);
906 if (!node
->u
.f
.degenerate
)
907 return isl_ast_expr_copy(node
->u
.f
.inc
);
908 return isl_ast_expr_alloc_int_si(isl_ast_node_get_ctx(node
), 1);
911 /* Replace the then branch of the if node "node" by "child".
913 __isl_give isl_ast_node
*isl_ast_node_if_set_then(
914 __isl_take isl_ast_node
*node
, __isl_take isl_ast_node
*child
)
916 node
= isl_ast_node_cow(node
);
919 if (node
->type
!= isl_ast_node_if
)
920 isl_die(isl_ast_node_get_ctx(node
), isl_error_invalid
,
921 "not an if node", goto error
);
923 isl_ast_node_free(node
->u
.i
.then
);
924 node
->u
.i
.then
= child
;
928 isl_ast_node_free(node
);
929 isl_ast_node_free(child
);
933 __isl_give isl_ast_node
*isl_ast_node_if_get_then(
934 __isl_keep isl_ast_node
*node
)
938 if (node
->type
!= isl_ast_node_if
)
939 isl_die(isl_ast_node_get_ctx(node
), isl_error_invalid
,
940 "not an if node", return NULL
);
941 return isl_ast_node_copy(node
->u
.i
.then
);
944 int isl_ast_node_if_has_else(
945 __isl_keep isl_ast_node
*node
)
949 if (node
->type
!= isl_ast_node_if
)
950 isl_die(isl_ast_node_get_ctx(node
), isl_error_invalid
,
951 "not an if node", return -1);
952 return node
->u
.i
.else_node
!= NULL
;
955 __isl_give isl_ast_node
*isl_ast_node_if_get_else(
956 __isl_keep isl_ast_node
*node
)
960 if (node
->type
!= isl_ast_node_if
)
961 isl_die(isl_ast_node_get_ctx(node
), isl_error_invalid
,
962 "not an if node", return NULL
);
963 return isl_ast_node_copy(node
->u
.i
.else_node
);
966 __isl_give isl_ast_expr
*isl_ast_node_if_get_cond(
967 __isl_keep isl_ast_node
*node
)
971 if (node
->type
!= isl_ast_node_if
)
972 isl_die(isl_ast_node_get_ctx(node
), isl_error_invalid
,
973 "not a guard node", return NULL
);
974 return isl_ast_expr_copy(node
->u
.i
.guard
);
977 __isl_give isl_ast_node_list
*isl_ast_node_block_get_children(
978 __isl_keep isl_ast_node
*node
)
982 if (node
->type
!= isl_ast_node_block
)
983 isl_die(isl_ast_node_get_ctx(node
), isl_error_invalid
,
984 "not a block node", return NULL
);
985 return isl_ast_node_list_copy(node
->u
.b
.children
);
988 __isl_give isl_ast_expr
*isl_ast_node_user_get_expr(
989 __isl_keep isl_ast_node
*node
)
994 return isl_ast_expr_copy(node
->u
.e
.expr
);
997 __isl_give isl_id
*isl_ast_node_get_annotation(__isl_keep isl_ast_node
*node
)
999 return node
? isl_id_copy(node
->annotation
) : NULL
;
1002 /* Replace node->annotation by "annotation".
1004 __isl_give isl_ast_node
*isl_ast_node_set_annotation(
1005 __isl_take isl_ast_node
*node
, __isl_take isl_id
*annotation
)
1007 node
= isl_ast_node_cow(node
);
1008 if (!node
|| !annotation
)
1011 isl_id_free(node
->annotation
);
1012 node
->annotation
= annotation
;
1016 isl_id_free(annotation
);
1017 return isl_ast_node_free(node
);
1020 /* Textual C representation of the various operators.
1022 static char *op_str
[] = {
1023 [isl_ast_op_and
] = "&&",
1024 [isl_ast_op_and_then
] = "&&",
1025 [isl_ast_op_or
] = "||",
1026 [isl_ast_op_or_else
] = "||",
1027 [isl_ast_op_max
] = "max",
1028 [isl_ast_op_min
] = "min",
1029 [isl_ast_op_minus
] = "-",
1030 [isl_ast_op_add
] = "+",
1031 [isl_ast_op_sub
] = "-",
1032 [isl_ast_op_mul
] = "*",
1033 [isl_ast_op_pdiv_q
] = "/",
1034 [isl_ast_op_pdiv_r
] = "%",
1035 [isl_ast_op_div
] = "/",
1036 [isl_ast_op_eq
] = "==",
1037 [isl_ast_op_le
] = "<=",
1038 [isl_ast_op_ge
] = ">=",
1039 [isl_ast_op_lt
] = "<",
1040 [isl_ast_op_gt
] = ">"
1043 /* Precedence in C of the various operators.
1044 * Based on http://en.wikipedia.org/wiki/Operators_in_C_and_C++
1045 * Lowest value means highest precedence.
1047 static int op_prec
[] = {
1048 [isl_ast_op_and
] = 13,
1049 [isl_ast_op_and_then
] = 13,
1050 [isl_ast_op_or
] = 14,
1051 [isl_ast_op_or_else
] = 14,
1052 [isl_ast_op_max
] = 2,
1053 [isl_ast_op_min
] = 2,
1054 [isl_ast_op_minus
] = 3,
1055 [isl_ast_op_add
] = 6,
1056 [isl_ast_op_sub
] = 6,
1057 [isl_ast_op_mul
] = 5,
1058 [isl_ast_op_div
] = 5,
1059 [isl_ast_op_fdiv_q
] = 2,
1060 [isl_ast_op_pdiv_q
] = 5,
1061 [isl_ast_op_pdiv_r
] = 5,
1062 [isl_ast_op_cond
] = 15,
1063 [isl_ast_op_select
] = 15,
1064 [isl_ast_op_eq
] = 9,
1065 [isl_ast_op_le
] = 8,
1066 [isl_ast_op_ge
] = 8,
1067 [isl_ast_op_lt
] = 8,
1068 [isl_ast_op_gt
] = 8,
1069 [isl_ast_op_call
] = 2
1072 /* Is the operator left-to-right associative?
1074 static int op_left
[] = {
1075 [isl_ast_op_and
] = 1,
1076 [isl_ast_op_and_then
] = 1,
1077 [isl_ast_op_or
] = 1,
1078 [isl_ast_op_or_else
] = 1,
1079 [isl_ast_op_max
] = 1,
1080 [isl_ast_op_min
] = 1,
1081 [isl_ast_op_minus
] = 0,
1082 [isl_ast_op_add
] = 1,
1083 [isl_ast_op_sub
] = 1,
1084 [isl_ast_op_mul
] = 1,
1085 [isl_ast_op_div
] = 1,
1086 [isl_ast_op_fdiv_q
] = 1,
1087 [isl_ast_op_pdiv_q
] = 1,
1088 [isl_ast_op_pdiv_r
] = 1,
1089 [isl_ast_op_cond
] = 0,
1090 [isl_ast_op_select
] = 0,
1091 [isl_ast_op_eq
] = 1,
1092 [isl_ast_op_le
] = 1,
1093 [isl_ast_op_ge
] = 1,
1094 [isl_ast_op_lt
] = 1,
1095 [isl_ast_op_gt
] = 1,
1096 [isl_ast_op_call
] = 1
1099 static int is_and(enum isl_ast_op_type op
)
1101 return op
== isl_ast_op_and
|| op
== isl_ast_op_and_then
;
1104 static int is_or(enum isl_ast_op_type op
)
1106 return op
== isl_ast_op_or
|| op
== isl_ast_op_or_else
;
1109 static int is_add_sub(enum isl_ast_op_type op
)
1111 return op
== isl_ast_op_add
|| op
== isl_ast_op_sub
;
1114 static int is_div_mod(enum isl_ast_op_type op
)
1116 return op
== isl_ast_op_div
|| op
== isl_ast_op_pdiv_r
;
1119 /* Do we need/want parentheses around "expr" as a subexpression of
1120 * an "op" operation? If "left" is set, then "expr" is the left-most
1123 * We only need parentheses if "expr" represents an operation.
1125 * If op has a higher precedence than expr->u.op.op, then we need
1127 * If op and expr->u.op.op have the same precedence, but the operations
1128 * are performed in an order that is different from the associativity,
1129 * then we need parentheses.
1131 * An and inside an or technically does not require parentheses,
1132 * but some compilers complain about that, so we add them anyway.
1134 * Computations such as "a / b * c" and "a % b + c" can be somewhat
1135 * difficult to read, so we add parentheses for those as well.
1137 static int sub_expr_need_parens(enum isl_ast_op_type op
,
1138 __isl_keep isl_ast_expr
*expr
, int left
)
1140 if (expr
->type
!= isl_ast_expr_op
)
1143 if (op_prec
[expr
->u
.op
.op
] > op_prec
[op
])
1145 if (op_prec
[expr
->u
.op
.op
] == op_prec
[op
] && left
!= op_left
[op
])
1148 if (is_or(op
) && is_and(expr
->u
.op
.op
))
1150 if (op
== isl_ast_op_mul
&& expr
->u
.op
.op
!= isl_ast_op_mul
&&
1151 op_prec
[expr
->u
.op
.op
] == op_prec
[op
])
1153 if (is_add_sub(op
) && is_div_mod(expr
->u
.op
.op
))
1159 /* Print "expr" as a subexpression of an "op" operation.
1160 * If "left" is set, then "expr" is the left-most operand.
1162 static __isl_give isl_printer
*print_sub_expr(__isl_take isl_printer
*p
,
1163 enum isl_ast_op_type op
, __isl_keep isl_ast_expr
*expr
, int left
)
1167 need_parens
= sub_expr_need_parens(op
, expr
, left
);
1170 p
= isl_printer_print_str(p
, "(");
1171 p
= isl_printer_print_ast_expr(p
, expr
);
1173 p
= isl_printer_print_str(p
, ")");
1177 /* Print a min or max reduction "expr".
1179 static __isl_give isl_printer
*print_min_max(__isl_take isl_printer
*p
,
1180 __isl_keep isl_ast_expr
*expr
)
1184 for (i
= 1; i
< expr
->u
.op
.n_arg
; ++i
) {
1185 p
= isl_printer_print_str(p
, op_str
[expr
->u
.op
.op
]);
1186 p
= isl_printer_print_str(p
, "(");
1188 p
= isl_printer_print_ast_expr(p
, expr
->u
.op
.args
[0]);
1189 for (i
= 1; i
< expr
->u
.op
.n_arg
; ++i
) {
1190 p
= isl_printer_print_str(p
, ", ");
1191 p
= isl_printer_print_ast_expr(p
, expr
->u
.op
.args
[i
]);
1192 p
= isl_printer_print_str(p
, ")");
1198 /* Print a function call "expr".
1200 * The first argument represents the function to be called.
1202 static __isl_give isl_printer
*print_call(__isl_take isl_printer
*p
,
1203 __isl_keep isl_ast_expr
*expr
)
1207 p
= isl_printer_print_ast_expr(p
, expr
->u
.op
.args
[0]);
1208 p
= isl_printer_print_str(p
, "(");
1209 for (i
= 1; i
< expr
->u
.op
.n_arg
; ++i
) {
1211 p
= isl_printer_print_str(p
, ", ");
1212 p
= isl_printer_print_ast_expr(p
, expr
->u
.op
.args
[i
]);
1214 p
= isl_printer_print_str(p
, ")");
1219 /* Print "expr" to "p".
1221 * If we are printing in isl format, then we also print an indication
1222 * of the size of the expression (if it was computed).
1224 __isl_give isl_printer
*isl_printer_print_ast_expr(__isl_take isl_printer
*p
,
1225 __isl_keep isl_ast_expr
*expr
)
1230 return isl_printer_free(p
);
1232 switch (expr
->type
) {
1233 case isl_ast_expr_op
:
1234 if (expr
->u
.op
.op
== isl_ast_op_call
) {
1235 p
= print_call(p
, expr
);
1238 if (expr
->u
.op
.n_arg
== 1) {
1239 p
= isl_printer_print_str(p
, op_str
[expr
->u
.op
.op
]);
1240 p
= print_sub_expr(p
, expr
->u
.op
.op
,
1241 expr
->u
.op
.args
[0], 0);
1244 if (expr
->u
.op
.op
== isl_ast_op_fdiv_q
) {
1245 p
= isl_printer_print_str(p
, "floord(");
1246 p
= isl_printer_print_ast_expr(p
, expr
->u
.op
.args
[0]);
1247 p
= isl_printer_print_str(p
, ", ");
1248 p
= isl_printer_print_ast_expr(p
, expr
->u
.op
.args
[1]);
1249 p
= isl_printer_print_str(p
, ")");
1252 if (expr
->u
.op
.op
== isl_ast_op_max
||
1253 expr
->u
.op
.op
== isl_ast_op_min
) {
1254 p
= print_min_max(p
, expr
);
1257 if (expr
->u
.op
.op
== isl_ast_op_cond
||
1258 expr
->u
.op
.op
== isl_ast_op_select
) {
1259 p
= isl_printer_print_ast_expr(p
, expr
->u
.op
.args
[0]);
1260 p
= isl_printer_print_str(p
, " ? ");
1261 p
= isl_printer_print_ast_expr(p
, expr
->u
.op
.args
[1]);
1262 p
= isl_printer_print_str(p
, " : ");
1263 p
= isl_printer_print_ast_expr(p
, expr
->u
.op
.args
[2]);
1266 if (expr
->u
.op
.n_arg
!= 2)
1267 isl_die(isl_printer_get_ctx(p
), isl_error_internal
,
1268 "operation should have two arguments",
1270 p
= print_sub_expr(p
, expr
->u
.op
.op
, expr
->u
.op
.args
[0], 1);
1271 p
= isl_printer_print_str(p
, " ");
1272 p
= isl_printer_print_str(p
, op_str
[expr
->u
.op
.op
]);
1273 p
= isl_printer_print_str(p
, " ");
1274 p
= print_sub_expr(p
, expr
->u
.op
.op
, expr
->u
.op
.args
[1], 0);
1276 case isl_ast_expr_id
:
1277 p
= isl_printer_print_str(p
, isl_id_get_name(expr
->u
.id
));
1279 case isl_ast_expr_int
:
1280 p
= isl_printer_print_isl_int(p
, expr
->u
.i
);
1282 case isl_ast_expr_error
:
1288 isl_printer_free(p
);
1292 /* Print "node" to "p" in "isl format".
1294 static __isl_give isl_printer
*print_ast_node_isl(__isl_take isl_printer
*p
,
1295 __isl_keep isl_ast_node
*node
)
1297 p
= isl_printer_print_str(p
, "(");
1298 switch (node
->type
) {
1299 case isl_ast_node_for
:
1300 if (node
->u
.f
.degenerate
) {
1301 p
= isl_printer_print_ast_expr(p
, node
->u
.f
.init
);
1303 p
= isl_printer_print_str(p
, "init: ");
1304 p
= isl_printer_print_ast_expr(p
, node
->u
.f
.init
);
1305 p
= isl_printer_print_str(p
, ", ");
1306 p
= isl_printer_print_str(p
, "cond: ");
1307 p
= isl_printer_print_ast_expr(p
, node
->u
.f
.cond
);
1308 p
= isl_printer_print_str(p
, ", ");
1309 p
= isl_printer_print_str(p
, "inc: ");
1310 p
= isl_printer_print_ast_expr(p
, node
->u
.f
.inc
);
1312 if (node
->u
.f
.body
) {
1313 p
= isl_printer_print_str(p
, ", ");
1314 p
= isl_printer_print_str(p
, "body: ");
1315 p
= isl_printer_print_ast_node(p
, node
->u
.f
.body
);
1318 case isl_ast_node_user
:
1319 p
= isl_printer_print_ast_expr(p
, node
->u
.e
.expr
);
1321 case isl_ast_node_if
:
1322 p
= isl_printer_print_str(p
, "guard: ");
1323 p
= isl_printer_print_ast_expr(p
, node
->u
.i
.guard
);
1324 if (node
->u
.i
.then
) {
1325 p
= isl_printer_print_str(p
, ", ");
1326 p
= isl_printer_print_str(p
, "then: ");
1327 p
= isl_printer_print_ast_node(p
, node
->u
.i
.then
);
1329 if (node
->u
.i
.else_node
) {
1330 p
= isl_printer_print_str(p
, ", ");
1331 p
= isl_printer_print_str(p
, "else: ");
1332 p
= isl_printer_print_ast_node(p
, node
->u
.i
.else_node
);
1335 case isl_ast_node_block
:
1336 p
= isl_printer_print_ast_node_list(p
, node
->u
.b
.children
);
1341 p
= isl_printer_print_str(p
, ")");
1345 /* Do we need to print a block around the body "node" of a for or if node?
1347 * If the node is a block, then we need to print a block.
1348 * Also if the node is a degenerate for then we will print it as
1349 * an assignment followed by the body of the for loop, so we need a block
1352 static int need_block(__isl_keep isl_ast_node
*node
)
1354 if (node
->type
== isl_ast_node_block
)
1356 if (node
->type
== isl_ast_node_for
&& node
->u
.f
.degenerate
)
1361 static __isl_give isl_printer
*print_ast_node_c(__isl_take isl_printer
*p
,
1362 __isl_keep isl_ast_node
*node
,
1363 __isl_keep isl_ast_print_options
*options
, int in_block
, int in_list
);
1364 static __isl_give isl_printer
*print_if_c(__isl_take isl_printer
*p
,
1365 __isl_keep isl_ast_node
*node
,
1366 __isl_keep isl_ast_print_options
*options
, int new_line
);
1368 /* Print the body "node" of a for or if node.
1369 * If "else_node" is set, then it is printed as well.
1371 * We first check if we need to print out a block.
1372 * We always print out a block if there is an else node to make
1373 * sure that the else node is matched to the correct if node.
1375 * If the else node is itself an if, then we print it as
1379 * Otherwise the else node is printed as
1384 static __isl_give isl_printer
*print_body_c(__isl_take isl_printer
*p
,
1385 __isl_keep isl_ast_node
*node
, __isl_keep isl_ast_node
*else_node
,
1386 __isl_keep isl_ast_print_options
*options
)
1389 return isl_printer_free(p
);
1391 if (!else_node
&& !need_block(node
)) {
1392 p
= isl_printer_end_line(p
);
1393 p
= isl_printer_indent(p
, 2);
1394 p
= isl_ast_node_print(node
, p
,
1395 isl_ast_print_options_copy(options
));
1396 p
= isl_printer_indent(p
, -2);
1400 p
= isl_printer_print_str(p
, " {");
1401 p
= isl_printer_end_line(p
);
1402 p
= isl_printer_indent(p
, 2);
1403 p
= print_ast_node_c(p
, node
, options
, 1, 0);
1404 p
= isl_printer_indent(p
, -2);
1405 p
= isl_printer_start_line(p
);
1406 p
= isl_printer_print_str(p
, "}");
1408 if (else_node
->type
== isl_ast_node_if
) {
1409 p
= isl_printer_print_str(p
, " else ");
1410 p
= print_if_c(p
, else_node
, options
, 0);
1412 p
= isl_printer_print_str(p
, " else");
1413 p
= print_body_c(p
, else_node
, NULL
, options
);
1416 p
= isl_printer_end_line(p
);
1421 /* Print the start of a compound statement.
1423 static __isl_give isl_printer
*start_block(__isl_take isl_printer
*p
)
1425 p
= isl_printer_start_line(p
);
1426 p
= isl_printer_print_str(p
, "{");
1427 p
= isl_printer_end_line(p
);
1428 p
= isl_printer_indent(p
, 2);
1433 /* Print the end of a compound statement.
1435 static __isl_give isl_printer
*end_block(__isl_take isl_printer
*p
)
1437 p
= isl_printer_indent(p
, -2);
1438 p
= isl_printer_start_line(p
);
1439 p
= isl_printer_print_str(p
, "}");
1440 p
= isl_printer_end_line(p
);
1445 /* Print the for node "node".
1447 * If the for node is degenerate, it is printed as
1449 * type iterator = init;
1452 * Otherwise, it is printed as
1454 * for (type iterator = init; cond; iterator += inc)
1457 * "in_block" is set if we are currently inside a block.
1458 * "in_list" is set if the current node is not alone in the block.
1459 * If we are not in a block or if the current not is not alone in the block
1460 * then we print a block around a degenerate for loop such that the variable
1461 * declaration will not conflict with any potential other declaration
1462 * of the same variable.
1464 static __isl_give isl_printer
*print_for_c(__isl_take isl_printer
*p
,
1465 __isl_keep isl_ast_node
*node
,
1466 __isl_keep isl_ast_print_options
*options
, int in_block
, int in_list
)
1472 type
= isl_options_get_ast_iterator_type(isl_printer_get_ctx(p
));
1473 if (!node
->u
.f
.degenerate
) {
1474 id
= isl_ast_expr_get_id(node
->u
.f
.iterator
);
1475 name
= isl_id_get_name(id
);
1477 p
= isl_printer_start_line(p
);
1478 p
= isl_printer_print_str(p
, "for (");
1479 p
= isl_printer_print_str(p
, type
);
1480 p
= isl_printer_print_str(p
, " ");
1481 p
= isl_printer_print_str(p
, name
);
1482 p
= isl_printer_print_str(p
, " = ");
1483 p
= isl_printer_print_ast_expr(p
, node
->u
.f
.init
);
1484 p
= isl_printer_print_str(p
, "; ");
1485 p
= isl_printer_print_ast_expr(p
, node
->u
.f
.cond
);
1486 p
= isl_printer_print_str(p
, "; ");
1487 p
= isl_printer_print_str(p
, name
);
1488 p
= isl_printer_print_str(p
, " += ");
1489 p
= isl_printer_print_ast_expr(p
, node
->u
.f
.inc
);
1490 p
= isl_printer_print_str(p
, ")");
1491 p
= print_body_c(p
, node
->u
.f
.body
, NULL
, options
);
1493 id
= isl_ast_expr_get_id(node
->u
.f
.iterator
);
1494 name
= isl_id_get_name(id
);
1496 if (!in_block
|| in_list
)
1498 p
= isl_printer_start_line(p
);
1499 p
= isl_printer_print_str(p
, type
);
1500 p
= isl_printer_print_str(p
, " ");
1501 p
= isl_printer_print_str(p
, name
);
1502 p
= isl_printer_print_str(p
, " = ");
1503 p
= isl_printer_print_ast_expr(p
, node
->u
.f
.init
);
1504 p
= isl_printer_print_str(p
, ";");
1505 p
= isl_printer_end_line(p
);
1506 p
= print_ast_node_c(p
, node
->u
.f
.body
, options
, 1, 0);
1507 if (!in_block
|| in_list
)
1514 /* Print the if node "node".
1515 * If "new_line" is set then the if node should be printed on a new line.
1517 static __isl_give isl_printer
*print_if_c(__isl_take isl_printer
*p
,
1518 __isl_keep isl_ast_node
*node
,
1519 __isl_keep isl_ast_print_options
*options
, int new_line
)
1522 p
= isl_printer_start_line(p
);
1523 p
= isl_printer_print_str(p
, "if (");
1524 p
= isl_printer_print_ast_expr(p
, node
->u
.i
.guard
);
1525 p
= isl_printer_print_str(p
, ")");
1526 p
= print_body_c(p
, node
->u
.i
.then
, node
->u
.i
.else_node
, options
);
1531 /* Print the "node" to "p".
1533 * "in_block" is set if we are currently inside a block.
1534 * If so, we do not print a block around the children of a block node.
1535 * We do this to avoid an extra block around the body of a degenerate
1538 * "in_list" is set if the current node is not alone in the block.
1540 static __isl_give isl_printer
*print_ast_node_c(__isl_take isl_printer
*p
,
1541 __isl_keep isl_ast_node
*node
,
1542 __isl_keep isl_ast_print_options
*options
, int in_block
, int in_list
)
1544 switch (node
->type
) {
1545 case isl_ast_node_for
:
1546 if (options
->print_for
)
1547 return options
->print_for(p
,
1548 isl_ast_print_options_copy(options
),
1549 node
, options
->print_for_user
);
1550 p
= print_for_c(p
, node
, options
, in_block
, in_list
);
1552 case isl_ast_node_if
:
1553 p
= print_if_c(p
, node
, options
, 1);
1555 case isl_ast_node_block
:
1558 p
= isl_ast_node_list_print(node
->u
.b
.children
, p
, options
);
1562 case isl_ast_node_user
:
1563 if (options
->print_user
)
1564 return options
->print_user(p
,
1565 isl_ast_print_options_copy(options
),
1566 node
, options
->print_user_user
);
1567 p
= isl_printer_start_line(p
);
1568 p
= isl_printer_print_ast_expr(p
, node
->u
.e
.expr
);
1569 p
= isl_printer_print_str(p
, ";");
1570 p
= isl_printer_end_line(p
);
1572 case isl_ast_node_error
:
1578 /* Print the for node "node" to "p".
1580 __isl_give isl_printer
*isl_ast_node_for_print(__isl_keep isl_ast_node
*node
,
1581 __isl_take isl_printer
*p
, __isl_take isl_ast_print_options
*options
)
1583 if (!node
|| !options
)
1585 if (node
->type
!= isl_ast_node_for
)
1586 isl_die(isl_ast_node_get_ctx(node
), isl_error_invalid
,
1587 "not a for node", goto error
);
1588 p
= print_for_c(p
, node
, options
, 0, 0);
1589 isl_ast_print_options_free(options
);
1592 isl_ast_print_options_free(options
);
1593 isl_printer_free(p
);
1597 /* Print the if node "node" to "p".
1599 __isl_give isl_printer
*isl_ast_node_if_print(__isl_keep isl_ast_node
*node
,
1600 __isl_take isl_printer
*p
, __isl_take isl_ast_print_options
*options
)
1602 if (!node
|| !options
)
1604 if (node
->type
!= isl_ast_node_if
)
1605 isl_die(isl_ast_node_get_ctx(node
), isl_error_invalid
,
1606 "not an if node", goto error
);
1607 p
= print_if_c(p
, node
, options
, 1);
1608 isl_ast_print_options_free(options
);
1611 isl_ast_print_options_free(options
);
1612 isl_printer_free(p
);
1616 /* Print "node" to "p".
1618 __isl_give isl_printer
*isl_ast_node_print(__isl_keep isl_ast_node
*node
,
1619 __isl_take isl_printer
*p
, __isl_take isl_ast_print_options
*options
)
1621 if (!options
|| !node
)
1623 p
= print_ast_node_c(p
, node
, options
, 0, 0);
1624 isl_ast_print_options_free(options
);
1627 isl_ast_print_options_free(options
);
1628 isl_printer_free(p
);
1632 /* Print "node" to "p".
1634 __isl_give isl_printer
*isl_printer_print_ast_node(__isl_take isl_printer
*p
,
1635 __isl_keep isl_ast_node
*node
)
1638 isl_ast_print_options
*options
;
1643 format
= isl_printer_get_output_format(p
);
1645 case ISL_FORMAT_ISL
:
1646 p
= print_ast_node_isl(p
, node
);
1649 options
= isl_ast_print_options_alloc(isl_printer_get_ctx(p
));
1650 p
= isl_ast_node_print(node
, p
, options
);
1653 isl_die(isl_printer_get_ctx(p
), isl_error_unsupported
,
1654 "output format not supported for ast_node",
1655 return isl_printer_free(p
));
1661 /* Print the list of nodes "list" to "p".
1663 __isl_give isl_printer
*isl_ast_node_list_print(
1664 __isl_keep isl_ast_node_list
*list
, __isl_take isl_printer
*p
,
1665 __isl_keep isl_ast_print_options
*options
)
1669 if (!p
|| !list
|| !options
)
1670 return isl_printer_free(p
);
1672 for (i
= 0; i
< list
->n
; ++i
)
1673 p
= print_ast_node_c(p
, list
->p
[i
], options
, 1, 1);
1678 #define ISL_AST_MACRO_FLOORD (1 << 0)
1679 #define ISL_AST_MACRO_MIN (1 << 1)
1680 #define ISL_AST_MACRO_MAX (1 << 2)
1681 #define ISL_AST_MACRO_ALL (ISL_AST_MACRO_FLOORD | \
1682 ISL_AST_MACRO_MIN | \
1685 /* If "expr" contains an isl_ast_op_min, isl_ast_op_max or isl_ast_op_fdiv_q
1686 * then set the corresponding bit in "macros".
1688 static int ast_expr_required_macros(__isl_keep isl_ast_expr
*expr
, int macros
)
1692 if (macros
== ISL_AST_MACRO_ALL
)
1695 if (expr
->type
!= isl_ast_expr_op
)
1698 if (expr
->u
.op
.op
== isl_ast_op_min
)
1699 macros
|= ISL_AST_MACRO_MIN
;
1700 if (expr
->u
.op
.op
== isl_ast_op_max
)
1701 macros
|= ISL_AST_MACRO_MAX
;
1702 if (expr
->u
.op
.op
== isl_ast_op_fdiv_q
)
1703 macros
|= ISL_AST_MACRO_FLOORD
;
1705 for (i
= 0; i
< expr
->u
.op
.n_arg
; ++i
)
1706 macros
= ast_expr_required_macros(expr
->u
.op
.args
[i
], macros
);
1711 static int ast_node_list_required_macros(__isl_keep isl_ast_node_list
*list
,
1714 /* If "node" contains an isl_ast_op_min, isl_ast_op_max or isl_ast_op_fdiv_q
1715 * then set the corresponding bit in "macros".
1717 static int ast_node_required_macros(__isl_keep isl_ast_node
*node
, int macros
)
1719 if (macros
== ISL_AST_MACRO_ALL
)
1722 switch (node
->type
) {
1723 case isl_ast_node_for
:
1724 macros
= ast_expr_required_macros(node
->u
.f
.init
, macros
);
1725 if (!node
->u
.f
.degenerate
) {
1726 macros
= ast_expr_required_macros(node
->u
.f
.cond
,
1728 macros
= ast_expr_required_macros(node
->u
.f
.inc
,
1731 macros
= ast_node_required_macros(node
->u
.f
.body
, macros
);
1733 case isl_ast_node_if
:
1734 macros
= ast_expr_required_macros(node
->u
.i
.guard
, macros
);
1735 macros
= ast_node_required_macros(node
->u
.i
.then
, macros
);
1736 if (node
->u
.i
.else_node
)
1737 macros
= ast_node_required_macros(node
->u
.i
.else_node
,
1740 case isl_ast_node_block
:
1741 macros
= ast_node_list_required_macros(node
->u
.b
.children
,
1744 case isl_ast_node_user
:
1745 macros
= ast_expr_required_macros(node
->u
.e
.expr
, macros
);
1747 case isl_ast_node_error
:
1754 /* If "list" contains an isl_ast_op_min, isl_ast_op_max or isl_ast_op_fdiv_q
1755 * then set the corresponding bit in "macros".
1757 static int ast_node_list_required_macros(__isl_keep isl_ast_node_list
*list
,
1762 for (i
= 0; i
< list
->n
; ++i
)
1763 macros
= ast_node_required_macros(list
->p
[i
], macros
);
1768 /* Print a macro definition for the operator "type".
1770 __isl_give isl_printer
*isl_ast_op_type_print_macro(
1771 enum isl_ast_op_type type
, __isl_take isl_printer
*p
)
1774 case isl_ast_op_min
:
1775 p
= isl_printer_start_line(p
);
1776 p
= isl_printer_print_str(p
,
1777 "#define min(x,y) ((x) < (y) ? (x) : (y))");
1778 p
= isl_printer_end_line(p
);
1780 case isl_ast_op_max
:
1781 p
= isl_printer_start_line(p
);
1782 p
= isl_printer_print_str(p
,
1783 "#define max(x,y) ((x) > (y) ? (x) : (y))");
1784 p
= isl_printer_end_line(p
);
1786 case isl_ast_op_fdiv_q
:
1787 p
= isl_printer_start_line(p
);
1788 p
= isl_printer_print_str(p
,
1789 "#define floord(n,d) "
1790 "(((n)<0) ? -((-(n)+(d)-1)/(d)) : (n)/(d))");
1791 p
= isl_printer_end_line(p
);
1800 /* Call "fn" for each type of operation that appears in "node"
1801 * and that requires a macro definition.
1803 int isl_ast_node_foreach_ast_op_type(__isl_keep isl_ast_node
*node
,
1804 int (*fn
)(enum isl_ast_op_type type
, void *user
), void *user
)
1811 macros
= ast_node_required_macros(node
, 0);
1813 if (macros
& ISL_AST_MACRO_MIN
&& fn(isl_ast_op_min
, user
) < 0)
1815 if (macros
& ISL_AST_MACRO_MAX
&& fn(isl_ast_op_max
, user
) < 0)
1817 if (macros
& ISL_AST_MACRO_FLOORD
&& fn(isl_ast_op_fdiv_q
, user
) < 0)
1823 static int ast_op_type_print_macro(enum isl_ast_op_type type
, void *user
)
1825 isl_printer
**p
= user
;
1827 *p
= isl_ast_op_type_print_macro(type
, *p
);
1832 /* Print macro definitions for all the macros used in the result
1833 * of printing "node.
1835 __isl_give isl_printer
*isl_ast_node_print_macros(
1836 __isl_keep isl_ast_node
*node
, __isl_take isl_printer
*p
)
1838 if (isl_ast_node_foreach_ast_op_type(node
,
1839 &ast_op_type_print_macro
, &p
) < 0)
1840 return isl_printer_free(p
);