1 /* Implementation of subroutines for the GNU C++ pretty-printer.
2 Copyright (C) 2003-2018 Free Software Foundation, Inc.
3 Contributed by Gabriel Dos Reis <gdr@integrable-solutions.net>
5 This file is part of GCC.
7 GCC is free software; you can redistribute it and/or modify it under
8 the terms of the GNU General Public License as published by the Free
9 Software Foundation; either version 3, or (at your option) any later
12 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
13 WARRANTY; without even the implied warranty of MERCHANTABILITY or
14 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
17 You should have received a copy of the GNU General Public License
18 along with GCC; see the file COPYING3. If not see
19 <http://www.gnu.org/licenses/>. */
23 #include "coretypes.h"
25 #include "cxx-pretty-print.h"
26 #include "tree-pretty-print.h"
28 static void pp_cxx_unqualified_id (cxx_pretty_printer
*, tree
);
29 static void pp_cxx_nested_name_specifier (cxx_pretty_printer
*, tree
);
30 static void pp_cxx_qualified_id (cxx_pretty_printer
*, tree
);
31 static void pp_cxx_template_argument_list (cxx_pretty_printer
*, tree
);
32 static void pp_cxx_type_specifier_seq (cxx_pretty_printer
*, tree
);
33 static void pp_cxx_ptr_operator (cxx_pretty_printer
*, tree
);
34 static void pp_cxx_parameter_declaration_clause (cxx_pretty_printer
*, tree
);
35 static void pp_cxx_template_parameter (cxx_pretty_printer
*, tree
);
36 static void pp_cxx_cast_expression (cxx_pretty_printer
*, tree
);
37 static void pp_cxx_typeid_expression (cxx_pretty_printer
*, tree
);
38 static void pp_cxx_unary_left_fold_expression (cxx_pretty_printer
*, tree
);
39 static void pp_cxx_unary_right_fold_expression (cxx_pretty_printer
*, tree
);
40 static void pp_cxx_binary_fold_expression (cxx_pretty_printer
*, tree
);
44 pp_cxx_nonconsecutive_character (cxx_pretty_printer
*pp
, int c
)
46 const char *p
= pp_last_position_in_text (pp
);
48 if (p
!= NULL
&& *p
== c
)
49 pp_cxx_whitespace (pp
);
51 pp
->padding
= pp_none
;
54 #define pp_cxx_expression_list(PP, T) \
55 pp_c_expression_list (PP, T)
56 #define pp_cxx_space_for_pointer_operator(PP, T) \
57 pp_c_space_for_pointer_operator (PP, T)
58 #define pp_cxx_init_declarator(PP, T) \
59 pp_c_init_declarator (PP, T)
60 #define pp_cxx_call_argument_list(PP, T) \
61 pp_c_call_argument_list (PP, T)
64 pp_cxx_colon_colon (cxx_pretty_printer
*pp
)
67 pp
->padding
= pp_none
;
71 pp_cxx_begin_template_argument_list (cxx_pretty_printer
*pp
)
73 pp_cxx_nonconsecutive_character (pp
, '<');
77 pp_cxx_end_template_argument_list (cxx_pretty_printer
*pp
)
79 pp_cxx_nonconsecutive_character (pp
, '>');
83 pp_cxx_separate_with (cxx_pretty_printer
*pp
, int c
)
85 pp_separate_with (pp
, c
);
86 pp
->padding
= pp_none
;
91 /* conversion-function-id:
92 operator conversion-type-id
95 type-specifier-seq conversion-declarator(opt)
97 conversion-declarator:
98 ptr-operator conversion-declarator(opt) */
101 pp_cxx_conversion_function_id (cxx_pretty_printer
*pp
, tree t
)
103 pp_cxx_ws_string (pp
, "operator");
104 pp_cxx_type_specifier_seq (pp
, TREE_TYPE (t
));
108 pp_cxx_template_id (cxx_pretty_printer
*pp
, tree t
)
110 pp_cxx_unqualified_id (pp
, TREE_OPERAND (t
, 0));
111 pp_cxx_begin_template_argument_list (pp
);
112 pp_cxx_template_argument_list (pp
, TREE_OPERAND (t
, 1));
113 pp_cxx_end_template_argument_list (pp
);
116 /* Prints the unqualified part of the id-expression T.
121 conversion-function-id
126 pp_cxx_unqualified_id (cxx_pretty_printer
*pp
, tree t
)
128 enum tree_code code
= TREE_CODE (t
);
132 pp
->translate_string ("<return-value>");
151 case IDENTIFIER_NODE
:
153 pp
->translate_string ("<unnamed>");
154 else if (IDENTIFIER_CONV_OP_P (t
))
155 pp_cxx_conversion_function_id (pp
, t
);
157 pp_cxx_tree_identifier (pp
, t
);
160 case TEMPLATE_ID_EXPR
:
161 pp_cxx_template_id (pp
, t
);
165 pp_cxx_unqualified_id (pp
, BASELINK_FUNCTIONS (t
));
172 case UNBOUND_CLASS_TEMPLATE
:
173 pp_cxx_unqualified_id (pp
, TYPE_NAME (t
));
174 if (CLASS_TYPE_P (t
) && CLASSTYPE_USE_TEMPLATE (t
))
176 pp_cxx_begin_template_argument_list (pp
);
177 pp_cxx_template_argument_list (pp
, INNERMOST_TEMPLATE_ARGS
178 (CLASSTYPE_TI_ARGS (t
)));
179 pp_cxx_end_template_argument_list (pp
);
184 pp_cxx_complement (pp
);
185 pp_cxx_unqualified_id (pp
, TREE_OPERAND (t
, 0));
188 case TEMPLATE_TYPE_PARM
:
189 case TEMPLATE_TEMPLATE_PARM
:
190 if (TYPE_IDENTIFIER (t
))
191 pp_cxx_unqualified_id (pp
, TYPE_IDENTIFIER (t
));
193 pp_cxx_canonical_template_parameter (pp
, t
);
196 case TEMPLATE_PARM_INDEX
:
197 pp_cxx_unqualified_id (pp
, TEMPLATE_PARM_DECL (t
));
200 case BOUND_TEMPLATE_TEMPLATE_PARM
:
201 pp_cxx_cv_qualifier_seq (pp
, t
);
202 pp_cxx_unqualified_id (pp
, TYPE_IDENTIFIER (t
));
203 pp_cxx_begin_template_argument_list (pp
);
204 pp_cxx_template_argument_list (pp
, TYPE_TI_ARGS (t
));
205 pp_cxx_end_template_argument_list (pp
);
209 pp_unsupported_tree (pp
, t
);
214 /* Pretty-print out the token sequence ":: template" in template codes
215 where it is needed to "inline declare" the (following) member as
216 a template. This situation arises when SCOPE of T is dependent
217 on template parameters. */
220 pp_cxx_template_keyword_if_needed (cxx_pretty_printer
*pp
, tree scope
, tree t
)
222 if (TREE_CODE (t
) == TEMPLATE_ID_EXPR
223 && TYPE_P (scope
) && dependent_type_p (scope
))
224 pp_cxx_ws_string (pp
, "template");
227 /* nested-name-specifier:
228 class-or-namespace-name :: nested-name-specifier(opt)
229 class-or-namespace-name :: template nested-name-specifier */
232 pp_cxx_nested_name_specifier (cxx_pretty_printer
*pp
, tree t
)
234 if (!SCOPE_FILE_SCOPE_P (t
) && t
!= pp
->enclosing_scope
)
236 tree scope
= get_containing_scope (t
);
237 pp_cxx_nested_name_specifier (pp
, scope
);
238 pp_cxx_template_keyword_if_needed (pp
, scope
, t
);
239 pp_cxx_unqualified_id (pp
, t
);
240 pp_cxx_colon_colon (pp
);
245 nested-name-specifier template(opt) unqualified-id */
248 pp_cxx_qualified_id (cxx_pretty_printer
*pp
, tree t
)
250 switch (TREE_CODE (t
))
252 /* A pointer-to-member is always qualified. */
254 pp_cxx_nested_name_specifier (pp
, PTRMEM_CST_CLASS (t
));
255 pp_cxx_unqualified_id (pp
, PTRMEM_CST_MEMBER (t
));
258 /* In Standard C++, functions cannot possibly be used as
259 nested-name-specifiers. However, there are situations where
260 is "makes sense" to output the surrounding function name for the
261 purpose of emphasizing on the scope kind. Just printing the
262 function name might not be sufficient as it may be overloaded; so,
263 we decorate the function with its signature too.
264 FIXME: This is probably the wrong pretty-printing for conversion
265 functions and some function templates. */
270 if (DECL_FUNCTION_MEMBER_P (t
))
271 pp_cxx_nested_name_specifier (pp
, DECL_CONTEXT (t
));
272 pp_cxx_unqualified_id
273 (pp
, DECL_CONSTRUCTOR_P (t
) ? DECL_CONTEXT (t
) : t
);
274 pp_cxx_parameter_declaration_clause (pp
, TREE_TYPE (t
));
279 pp_cxx_nested_name_specifier (pp
, TREE_OPERAND (t
, 0));
280 pp_cxx_unqualified_id (pp
, TREE_OPERAND (t
, 1));
285 tree scope
= get_containing_scope (t
);
286 if (scope
!= pp
->enclosing_scope
)
288 pp_cxx_nested_name_specifier (pp
, scope
);
289 pp_cxx_template_keyword_if_needed (pp
, scope
, t
);
291 pp_cxx_unqualified_id (pp
, t
);
297 /* Given a value e of ENUMERAL_TYPE:
298 Print out the first ENUMERATOR id with value e, if one is found,
299 (including nested names but excluding the enum name if unscoped)
300 else print out the value as a C-style cast (type-id)value. */
303 pp_cxx_enumeration_constant (cxx_pretty_printer
*pp
, tree e
)
305 tree type
= TREE_TYPE (e
);
308 /* Find the name of this constant. */
309 for (value
= TYPE_VALUES (type
);
311 && !tree_int_cst_equal (DECL_INITIAL (TREE_VALUE (value
)), e
);
312 value
= TREE_CHAIN (value
))
315 if (value
!= NULL_TREE
)
317 if (!ENUM_IS_SCOPED (type
))
318 type
= get_containing_scope (type
);
319 pp_cxx_nested_name_specifier (pp
, type
);
320 pp
->id_expression (TREE_PURPOSE (value
));
324 /* Value must have been cast. */
325 pp_c_type_cast (pp
, type
);
326 pp_c_integer_constant (pp
, e
);
332 cxx_pretty_printer::constant (tree t
)
334 switch (TREE_CODE (t
))
338 const bool in_parens
= PAREN_STRING_LITERAL_P (t
);
340 pp_cxx_left_paren (this);
341 c_pretty_printer::constant (t
);
343 pp_cxx_right_paren (this);
348 if (NULLPTR_TYPE_P (TREE_TYPE (t
)))
350 pp_string (this, "nullptr");
353 else if (TREE_CODE (TREE_TYPE (t
)) == ENUMERAL_TYPE
)
355 pp_cxx_enumeration_constant (this, t
);
361 c_pretty_printer::constant (t
);
371 cxx_pretty_printer::id_expression (tree t
)
373 if (TREE_CODE (t
) == OVERLOAD
)
375 if (DECL_P (t
) && DECL_CONTEXT (t
))
376 pp_cxx_qualified_id (this, t
);
378 pp_cxx_unqualified_id (this, t
);
381 /* user-defined literal:
385 pp_cxx_userdef_literal (cxx_pretty_printer
*pp
, tree t
)
387 pp
->constant (USERDEF_LITERAL_VALUE (t
));
388 pp
->id_expression (USERDEF_LITERAL_SUFFIX_ID (t
));
392 /* primary-expression:
396 :: operator-function-id
402 __builtin_va_arg ( assignment-expression , type-id )
403 __builtin_offsetof ( type-id, offsetof-expression )
404 __builtin_addressof ( expression )
406 __has_nothrow_assign ( type-id )
407 __has_nothrow_constructor ( type-id )
408 __has_nothrow_copy ( type-id )
409 __has_trivial_assign ( type-id )
410 __has_trivial_constructor ( type-id )
411 __has_trivial_copy ( type-id )
412 __has_unique_object_representations ( type-id )
413 __has_trivial_destructor ( type-id )
414 __has_virtual_destructor ( type-id )
415 __is_abstract ( type-id )
416 __is_base_of ( type-id , type-id )
417 __is_class ( type-id )
418 __is_empty ( type-id )
419 __is_enum ( type-id )
420 __is_literal_type ( type-id )
422 __is_polymorphic ( type-id )
423 __is_std_layout ( type-id )
424 __is_trivial ( type-id )
425 __is_union ( type-id ) */
428 cxx_pretty_printer::primary_expression (tree t
)
430 switch (TREE_CODE (t
))
440 case USERDEF_LITERAL
:
441 pp_cxx_userdef_literal (this, t
);
445 t
= BASELINK_FUNCTIONS (t
);
458 case TEMPLATE_TYPE_PARM
:
459 case TEMPLATE_TEMPLATE_PARM
:
460 case TEMPLATE_PARM_INDEX
:
461 pp_cxx_unqualified_id (this, t
);
465 pp_cxx_left_paren (this);
466 statement (STMT_EXPR_STMT (t
));
467 pp_cxx_right_paren (this);
471 pp_cxx_trait_expression (this, t
);
475 pp_cxx_va_arg_expression (this, t
);
479 pp_cxx_offsetof_expression (this, t
);
483 pp_cxx_addressof_expression (this, t
);
487 pp_cxx_requires_expr (this, t
);
491 c_pretty_printer::primary_expression (t
);
496 /* postfix-expression:
498 postfix-expression [ expression ]
499 postfix-expression ( expression-list(opt) )
500 simple-type-specifier ( expression-list(opt) )
501 typename ::(opt) nested-name-specifier identifier ( expression-list(opt) )
502 typename ::(opt) nested-name-specifier template(opt)
503 template-id ( expression-list(opt) )
504 postfix-expression . template(opt) ::(opt) id-expression
505 postfix-expression -> template(opt) ::(opt) id-expression
506 postfix-expression . pseudo-destructor-name
507 postfix-expression -> pseudo-destructor-name
508 postfix-expression ++
509 postfix-expression --
510 dynamic_cast < type-id > ( expression )
511 static_cast < type-id > ( expression )
512 reinterpret_cast < type-id > ( expression )
513 const_cast < type-id > ( expression )
514 typeid ( expression )
515 typeid ( type-id ) */
518 cxx_pretty_printer::postfix_expression (tree t
)
520 enum tree_code code
= TREE_CODE (t
);
527 tree fun
= cp_get_callee (t
);
528 tree saved_scope
= enclosing_scope
;
529 bool skipfirst
= false;
532 if (TREE_CODE (fun
) == ADDR_EXPR
)
533 fun
= TREE_OPERAND (fun
, 0);
535 /* In templates, where there is no way to tell whether a given
536 call uses an actual member function. So the parser builds
537 FUN as a COMPONENT_REF or a plain IDENTIFIER_NODE until
538 instantiation time. */
539 if (TREE_CODE (fun
) != FUNCTION_DECL
)
541 else if (DECL_NONSTATIC_MEMBER_FUNCTION_P (fun
))
543 tree object
= (code
== AGGR_INIT_EXPR
544 ? (AGGR_INIT_VIA_CTOR_P (t
)
545 ? AGGR_INIT_EXPR_SLOT (t
)
546 : AGGR_INIT_EXPR_ARG (t
, 0))
547 : CALL_EXPR_ARG (t
, 0));
549 while (TREE_CODE (object
) == NOP_EXPR
)
550 object
= TREE_OPERAND (object
, 0);
552 if (TREE_CODE (object
) == ADDR_EXPR
)
553 object
= TREE_OPERAND (object
, 0);
555 if (!TYPE_PTR_P (TREE_TYPE (object
)))
557 postfix_expression (object
);
562 postfix_expression (object
);
566 enclosing_scope
= strip_pointer_operator (TREE_TYPE (object
));
569 postfix_expression (fun
);
570 enclosing_scope
= saved_scope
;
571 pp_cxx_left_paren (this);
572 if (code
== AGGR_INIT_EXPR
)
574 aggr_init_expr_arg_iterator iter
;
575 FOR_EACH_AGGR_INIT_EXPR_ARG (arg
, iter
, t
)
582 if (more_aggr_init_expr_args_p (&iter
))
583 pp_cxx_separate_with (this, ',');
589 call_expr_arg_iterator iter
;
590 FOR_EACH_CALL_EXPR_ARG (arg
, iter
, t
)
597 if (more_call_expr_args_p (&iter
))
598 pp_cxx_separate_with (this, ',');
602 pp_cxx_right_paren (this);
604 if (code
== AGGR_INIT_EXPR
&& AGGR_INIT_VIA_CTOR_P (t
))
606 pp_cxx_separate_with (this, ',');
607 postfix_expression (AGGR_INIT_EXPR_SLOT (t
));
620 primary_expression (t
);
623 case DYNAMIC_CAST_EXPR
:
624 case STATIC_CAST_EXPR
:
625 case REINTERPRET_CAST_EXPR
:
626 case CONST_CAST_EXPR
:
627 if (code
== DYNAMIC_CAST_EXPR
)
628 pp_cxx_ws_string (this, "dynamic_cast");
629 else if (code
== STATIC_CAST_EXPR
)
630 pp_cxx_ws_string (this, "static_cast");
631 else if (code
== REINTERPRET_CAST_EXPR
)
632 pp_cxx_ws_string (this, "reinterpret_cast");
634 pp_cxx_ws_string (this, "const_cast");
635 pp_cxx_begin_template_argument_list (this);
636 type_id (TREE_TYPE (t
));
637 pp_cxx_end_template_argument_list (this);
638 pp_left_paren (this);
639 expression (TREE_OPERAND (t
, 0));
640 pp_right_paren (this);
643 case EMPTY_CLASS_EXPR
:
644 type_id (TREE_TYPE (t
));
645 pp_left_paren (this);
646 pp_right_paren (this);
650 pp_cxx_typeid_expression (this, t
);
653 case PSEUDO_DTOR_EXPR
:
654 postfix_expression (TREE_OPERAND (t
, 0));
656 if (TREE_OPERAND (t
, 1))
658 pp_cxx_qualified_id (this, TREE_OPERAND (t
, 1));
659 pp_cxx_colon_colon (this);
661 pp_complement (this);
662 pp_cxx_unqualified_id (this, TREE_OPERAND (t
, 2));
666 postfix_expression (TREE_OPERAND (t
, 0));
671 c_pretty_printer::postfix_expression (t
);
677 ::(opt) new new-placement(opt) new-type-id new-initializer(opt)
678 ::(opt) new new-placement(opt) ( type-id ) new-initializer(opt)
684 type-specifier-seq new-declarator(opt)
687 ptr-operator new-declarator(opt)
688 direct-new-declarator
690 direct-new-declarator
692 direct-new-declarator [ constant-expression ]
695 ( expression-list(opt) ) */
698 pp_cxx_new_expression (cxx_pretty_printer
*pp
, tree t
)
700 enum tree_code code
= TREE_CODE (t
);
701 tree type
= TREE_OPERAND (t
, 1);
702 tree init
= TREE_OPERAND (t
, 2);
707 if (NEW_EXPR_USE_GLOBAL (t
))
708 pp_cxx_colon_colon (pp
);
709 pp_cxx_ws_string (pp
, "new");
710 if (TREE_OPERAND (t
, 0))
712 pp_cxx_call_argument_list (pp
, TREE_OPERAND (t
, 0));
715 if (TREE_CODE (type
) == ARRAY_REF
)
716 type
= build_cplus_array_type
717 (TREE_OPERAND (type
, 0),
718 build_index_type (fold_build2_loc (input_location
,
719 MINUS_EXPR
, integer_type_node
,
720 TREE_OPERAND (type
, 1),
726 if (TREE_CODE (init
) == TREE_LIST
)
727 pp_c_expression_list (pp
, init
);
728 else if (init
== void_node
)
729 ; /* OK, empty initializer list. */
731 pp
->expression (init
);
737 pp_unsupported_tree (pp
, t
);
741 /* delete-expression:
742 ::(opt) delete cast-expression
743 ::(opt) delete [ ] cast-expression */
746 pp_cxx_delete_expression (cxx_pretty_printer
*pp
, tree t
)
748 enum tree_code code
= TREE_CODE (t
);
752 case VEC_DELETE_EXPR
:
753 if (DELETE_EXPR_USE_GLOBAL (t
))
754 pp_cxx_colon_colon (pp
);
755 pp_cxx_ws_string (pp
, "delete");
757 if (code
== VEC_DELETE_EXPR
758 || DELETE_EXPR_USE_VEC (t
))
760 pp_left_bracket (pp
);
761 pp_right_bracket (pp
);
764 pp_c_cast_expression (pp
, TREE_OPERAND (t
, 0));
768 pp_unsupported_tree (pp
, t
);
776 unary-operator cast-expression
777 sizeof unary-expression
779 sizeof ... ( identifier )
783 unary-operator: one of
787 __alignof__ unary-expression
788 __alignof__ ( type-id ) */
791 cxx_pretty_printer::unary_expression (tree t
)
793 enum tree_code code
= TREE_CODE (t
);
798 pp_cxx_new_expression (this, t
);
802 case VEC_DELETE_EXPR
:
803 pp_cxx_delete_expression (this, t
);
807 if (PACK_EXPANSION_P (TREE_OPERAND (t
, 0)))
809 pp_cxx_ws_string (this, "sizeof");
810 pp_cxx_ws_string (this, "...");
811 pp_cxx_whitespace (this);
812 pp_cxx_left_paren (this);
813 if (TYPE_P (TREE_OPERAND (t
, 0)))
814 type_id (TREE_OPERAND (t
, 0));
816 unary_expression (TREE_OPERAND (t
, 0));
817 pp_cxx_right_paren (this);
823 pp_cxx_ws_string (this, code
== SIZEOF_EXPR
? "sizeof" : "__alignof__");
824 pp_cxx_whitespace (this);
825 if (TREE_CODE (t
) == SIZEOF_EXPR
&& SIZEOF_EXPR_TYPE_P (t
))
827 pp_cxx_left_paren (this);
828 type_id (TREE_TYPE (TREE_OPERAND (t
, 0)));
829 pp_cxx_right_paren (this);
831 else if (TYPE_P (TREE_OPERAND (t
, 0)))
833 pp_cxx_left_paren (this);
834 type_id (TREE_OPERAND (t
, 0));
835 pp_cxx_right_paren (this);
838 unary_expression (TREE_OPERAND (t
, 0));
842 pp_cxx_ws_string (this, "@encode");
843 pp_cxx_whitespace (this);
844 pp_cxx_left_paren (this);
845 type_id (TREE_OPERAND (t
, 0));
846 pp_cxx_right_paren (this);
850 pp_cxx_ws_string (this, "noexcept");
851 pp_cxx_whitespace (this);
852 pp_cxx_left_paren (this);
853 expression (TREE_OPERAND (t
, 0));
854 pp_cxx_right_paren (this);
857 case UNARY_PLUS_EXPR
:
859 pp_cxx_cast_expression (this, TREE_OPERAND (t
, 0));
863 c_pretty_printer::unary_expression (t
);
870 ( type-id ) cast-expression */
873 pp_cxx_cast_expression (cxx_pretty_printer
*pp
, tree t
)
875 switch (TREE_CODE (t
))
878 case IMPLICIT_CONV_EXPR
:
879 pp
->type_id (TREE_TYPE (t
));
880 pp_cxx_call_argument_list (pp
, TREE_OPERAND (t
, 0));
884 pp_c_cast_expression (pp
, t
);
891 pm-expression .* cast-expression
892 pm-expression ->* cast-expression */
895 pp_cxx_pm_expression (cxx_pretty_printer
*pp
, tree t
)
897 switch (TREE_CODE (t
))
899 /* Handle unfortunate OFFSET_REF overloading here. */
901 if (TYPE_P (TREE_OPERAND (t
, 0)))
903 pp_cxx_qualified_id (pp
, t
);
909 pp_cxx_pm_expression (pp
, TREE_OPERAND (t
, 0));
910 if (TREE_CODE (t
) == MEMBER_REF
)
915 pp_cxx_cast_expression (pp
, TREE_OPERAND (t
, 1));
920 pp_cxx_cast_expression (pp
, t
);
925 /* multiplicative-expression:
927 multiplicative-expression * pm-expression
928 multiplicative-expression / pm-expression
929 multiplicative-expression % pm-expression */
932 cxx_pretty_printer::multiplicative_expression (tree e
)
934 enum tree_code code
= TREE_CODE (e
);
942 multiplicative_expression (TREE_OPERAND (e
, 0));
944 if (code
== MULT_EXPR
)
946 else if (code
!= TRUNC_MOD_EXPR
)
951 pp_cxx_pm_expression (this, TREE_OPERAND (e
, 1));
955 pp_cxx_pm_expression (this, e
);
960 /* conditional-expression:
961 logical-or-expression
962 logical-or-expression ? expression : assignment-expression */
965 cxx_pretty_printer::conditional_expression (tree e
)
967 if (TREE_CODE (e
) == COND_EXPR
)
969 pp_c_logical_or_expression (this, TREE_OPERAND (e
, 0));
973 expression (TREE_OPERAND (e
, 1));
975 assignment_expression (TREE_OPERAND (e
, 2));
978 pp_c_logical_or_expression (this, e
);
981 /* Pretty-print a compound assignment operator token as indicated by T. */
984 pp_cxx_assignment_operator (cxx_pretty_printer
*pp
, tree t
)
988 switch (TREE_CODE (t
))
1002 case TRUNC_DIV_EXPR
:
1006 case TRUNC_MOD_EXPR
:
1011 op
= get_tree_code_name (TREE_CODE (t
));
1015 pp_cxx_ws_string (pp
, op
);
1019 /* assignment-expression:
1020 conditional-expression
1021 logical-or-expression assignment-operator assignment-expression
1025 throw assignment-expression(opt)
1027 assignment-operator: one of
1028 = *= /= %= += -= >>= <<= &= ^= |= */
1031 cxx_pretty_printer::assignment_expression (tree e
)
1033 switch (TREE_CODE (e
))
1037 pp_c_logical_or_expression (this, TREE_OPERAND (e
, 0));
1041 assignment_expression (TREE_OPERAND (e
, 1));
1045 pp_cxx_ws_string (this, "throw");
1046 if (TREE_OPERAND (e
, 0))
1047 assignment_expression (TREE_OPERAND (e
, 0));
1051 pp_c_logical_or_expression (this, TREE_OPERAND (e
, 0));
1052 pp_cxx_assignment_operator (this, TREE_OPERAND (e
, 1));
1053 assignment_expression (TREE_OPERAND (e
, 2));
1057 conditional_expression (e
);
1063 cxx_pretty_printer::expression (tree t
)
1065 switch (TREE_CODE (t
))
1075 case USERDEF_LITERAL
:
1076 pp_cxx_userdef_literal (this, t
);
1080 pp_cxx_unqualified_id (this, t
);
1088 pp_cxx_qualified_id (this, t
);
1101 case TEMPLATE_TYPE_PARM
:
1102 case TEMPLATE_PARM_INDEX
:
1103 case TEMPLATE_TEMPLATE_PARM
:
1106 primary_expression (t
);
1110 case DYNAMIC_CAST_EXPR
:
1111 case STATIC_CAST_EXPR
:
1112 case REINTERPRET_CAST_EXPR
:
1113 case CONST_CAST_EXPR
:
1117 case EMPTY_CLASS_EXPR
:
1119 case PSEUDO_DTOR_EXPR
:
1120 case AGGR_INIT_EXPR
:
1122 postfix_expression (t
);
1127 pp_cxx_new_expression (this, t
);
1131 case VEC_DELETE_EXPR
:
1132 pp_cxx_delete_expression (this, t
);
1138 case UNARY_PLUS_EXPR
:
1139 unary_expression (t
);
1143 case IMPLICIT_CONV_EXPR
:
1144 pp_cxx_cast_expression (this, t
);
1150 pp_cxx_pm_expression (this, t
);
1154 case TRUNC_DIV_EXPR
:
1155 case TRUNC_MOD_EXPR
:
1156 case EXACT_DIV_EXPR
:
1158 multiplicative_expression (t
);
1162 conditional_expression (t
);
1169 assignment_expression (t
);
1172 case NON_DEPENDENT_EXPR
:
1173 case MUST_NOT_THROW_EXPR
:
1174 expression (TREE_OPERAND (t
, 0));
1177 case EXPR_PACK_EXPANSION
:
1178 expression (PACK_EXPANSION_PATTERN (t
));
1179 pp_cxx_ws_string (this, "...");
1182 case UNARY_LEFT_FOLD_EXPR
:
1183 pp_cxx_unary_left_fold_expression (this, t
);
1186 case UNARY_RIGHT_FOLD_EXPR
:
1187 pp_cxx_unary_right_fold_expression (this, t
);
1190 case BINARY_LEFT_FOLD_EXPR
:
1191 case BINARY_RIGHT_FOLD_EXPR
:
1192 pp_cxx_binary_fold_expression (this, t
);
1195 case TEMPLATE_ID_EXPR
:
1196 pp_cxx_template_id (this, t
);
1199 case NONTYPE_ARGUMENT_PACK
:
1201 tree args
= ARGUMENT_PACK_ARGS (t
);
1202 int i
, len
= TREE_VEC_LENGTH (args
);
1203 for (i
= 0; i
< len
; ++i
)
1206 pp_cxx_separate_with (this, ',');
1207 expression (TREE_VEC_ELT (args
, i
));
1213 pp_cxx_ws_string (this, "<lambda>");
1217 pp_cxx_trait_expression (this, t
);
1230 pp_cxx_constraint (this, t
);
1234 pp_cxx_left_paren (this);
1235 expression (TREE_OPERAND (t
, 0));
1236 pp_cxx_right_paren (this);
1240 c_pretty_printer::expression (t
);
1248 /* function-specifier:
1254 cxx_pretty_printer::function_specifier (tree t
)
1256 switch (TREE_CODE (t
))
1259 if (DECL_VIRTUAL_P (t
))
1260 pp_cxx_ws_string (this, "virtual");
1261 else if (DECL_CONSTRUCTOR_P (t
) && DECL_NONCONVERTING_P (t
))
1262 pp_cxx_ws_string (this, "explicit");
1264 c_pretty_printer::function_specifier (t
);
1271 /* decl-specifier-seq:
1272 decl-specifier-seq(opt) decl-specifier
1275 storage-class-specifier
1282 cxx_pretty_printer::declaration_specifiers (tree t
)
1284 switch (TREE_CODE (t
))
1290 storage_class_specifier (t
);
1291 declaration_specifiers (TREE_TYPE (t
));
1295 pp_cxx_ws_string (this, "typedef");
1296 declaration_specifiers (TREE_TYPE (t
));
1300 /* Constructors don't have return types. And conversion functions
1301 do not have a type-specifier in their return types. */
1302 if (DECL_CONSTRUCTOR_P (t
) || DECL_CONV_FN_P (t
))
1303 function_specifier (t
);
1304 else if (DECL_NONSTATIC_MEMBER_FUNCTION_P (t
))
1305 declaration_specifiers (TREE_TYPE (TREE_TYPE (t
)));
1307 c_pretty_printer::declaration_specifiers (t
);
1310 c_pretty_printer::declaration_specifiers (t
);
1315 /* simple-type-specifier:
1316 ::(opt) nested-name-specifier(opt) type-name
1317 ::(opt) nested-name-specifier(opt) template(opt) template-id
1331 cxx_pretty_printer::simple_type_specifier (tree t
)
1333 switch (TREE_CODE (t
))
1338 pp_cxx_qualified_id (this, t
);
1341 case TEMPLATE_TYPE_PARM
:
1342 case TEMPLATE_TEMPLATE_PARM
:
1343 case TEMPLATE_PARM_INDEX
:
1344 case BOUND_TEMPLATE_TEMPLATE_PARM
:
1345 pp_cxx_unqualified_id (this, t
);
1349 pp_cxx_ws_string (this, "typename");
1350 pp_cxx_nested_name_specifier (this, TYPE_CONTEXT (t
));
1351 pp_cxx_unqualified_id (this, TYPE_NAME (t
));
1355 c_pretty_printer::simple_type_specifier (t
);
1360 /* type-specifier-seq:
1361 type-specifier type-specifier-seq(opt)
1364 simple-type-specifier
1367 elaborated-type-specifier
1371 pp_cxx_type_specifier_seq (cxx_pretty_printer
*pp
, tree t
)
1373 switch (TREE_CODE (t
))
1376 case TEMPLATE_TYPE_PARM
:
1377 case TEMPLATE_TEMPLATE_PARM
:
1379 case BOUND_TEMPLATE_TEMPLATE_PARM
:
1380 pp_cxx_cv_qualifier_seq (pp
, t
);
1381 pp
->simple_type_specifier (t
);
1385 pp_cxx_type_specifier_seq (pp
, TREE_TYPE (t
));
1386 pp_cxx_space_for_pointer_operator (pp
, TREE_TYPE (t
));
1387 pp_cxx_nested_name_specifier (pp
, TYPE_METHOD_BASETYPE (t
));
1391 pp_cxx_ws_string (pp
, "decltype");
1392 pp_cxx_left_paren (pp
);
1393 pp
->expression (DECLTYPE_TYPE_EXPR (t
));
1394 pp_cxx_right_paren (pp
);
1398 if (TYPE_PTRMEMFUNC_P (t
))
1400 tree pfm
= TYPE_PTRMEMFUNC_FN_TYPE (t
);
1401 pp
->declaration_specifiers (TREE_TYPE (TREE_TYPE (pfm
)));
1402 pp_cxx_whitespace (pp
);
1403 pp_cxx_ptr_operator (pp
, t
);
1409 if (!(TREE_CODE (t
) == FUNCTION_DECL
&& DECL_CONSTRUCTOR_P (t
)))
1410 pp_c_specifier_qualifier_list (pp
, t
);
1415 * cv-qualifier-seq(opt)
1417 ::(opt) nested-name-specifier * cv-qualifier-seq(opt) */
1420 pp_cxx_ptr_operator (cxx_pretty_printer
*pp
, tree t
)
1422 if (!TYPE_P (t
) && TREE_CODE (t
) != TYPE_DECL
)
1424 switch (TREE_CODE (t
))
1426 case REFERENCE_TYPE
:
1428 if (TYPE_PTR_OR_PTRMEM_P (TREE_TYPE (t
)))
1429 pp_cxx_ptr_operator (pp
, TREE_TYPE (t
));
1430 pp_c_attributes_display (pp
, TYPE_ATTRIBUTES (TREE_TYPE (t
)));
1434 pp_cxx_cv_qualifier_seq (pp
, t
);
1441 if (TYPE_PTRMEMFUNC_P (t
))
1443 pp_cxx_left_paren (pp
);
1444 pp_cxx_nested_name_specifier (pp
, TYPE_PTRMEMFUNC_OBJECT_TYPE (t
));
1450 if (TYPE_PTRMEM_P (t
))
1452 if (TREE_CODE (TREE_TYPE (t
)) == ARRAY_TYPE
)
1453 pp_cxx_left_paren (pp
);
1454 pp_cxx_nested_name_specifier (pp
, TYPE_PTRMEM_CLASS_TYPE (t
));
1456 pp_cxx_cv_qualifier_seq (pp
, t
);
1462 pp_unsupported_tree (pp
, t
);
1468 pp_cxx_implicit_parameter_type (tree mf
)
1470 return class_of_this_parm (TREE_TYPE (mf
));
1474 parameter-declaration:
1475 decl-specifier-seq declarator
1476 decl-specifier-seq declarator = assignment-expression
1477 decl-specifier-seq abstract-declarator(opt)
1478 decl-specifier-seq abstract-declarator(opt) assignment-expression */
1481 pp_cxx_parameter_declaration (cxx_pretty_printer
*pp
, tree t
)
1483 pp
->declaration_specifiers (t
);
1485 pp
->abstract_declarator (t
);
1490 /* parameter-declaration-clause:
1491 parameter-declaration-list(opt) ...(opt)
1492 parameter-declaration-list , ...
1494 parameter-declaration-list:
1495 parameter-declaration
1496 parameter-declaration-list , parameter-declaration */
1499 pp_cxx_parameter_declaration_clause (cxx_pretty_printer
*pp
, tree t
)
1505 // For a requires clause or the explicit printing of a parameter list
1506 // we expect T to be a chain of PARM_DECLs. Otherwise, the list of
1507 // args and types are taken from the function decl T.
1508 if (TREE_CODE (t
) == PARM_DECL
)
1516 bool type_p
= TYPE_P (t
);
1517 args
= type_p
? NULL
: FUNCTION_FIRST_USER_PARM (t
);
1518 types
= type_p
? TYPE_ARG_TYPES (t
) : FUNCTION_FIRST_USER_PARMTYPE (t
);
1519 abstract
= args
== NULL
|| pp
->flags
& pp_c_flag_abstract
;
1523 /* Skip artificial parameter for nonstatic member functions. */
1524 if (TREE_CODE (t
) == METHOD_TYPE
)
1525 types
= TREE_CHAIN (types
);
1527 pp_cxx_left_paren (pp
);
1528 for (; args
; args
= TREE_CHAIN (args
), types
= TREE_CHAIN (types
))
1531 pp_cxx_separate_with (pp
, ',');
1533 pp_cxx_parameter_declaration (pp
, abstract
? TREE_VALUE (types
) : args
);
1534 if (!abstract
&& pp
->flags
& pp_cxx_flag_default_argument
)
1536 pp_cxx_whitespace (pp
);
1538 pp_cxx_whitespace (pp
);
1539 pp
->assignment_expression (TREE_PURPOSE (types
));
1542 pp_cxx_right_paren (pp
);
1545 /* exception-specification:
1546 throw ( type-id-list(opt) )
1550 type-id-list , type-id */
1553 pp_cxx_exception_specification (cxx_pretty_printer
*pp
, tree t
)
1555 tree ex_spec
= TYPE_RAISES_EXCEPTIONS (t
);
1556 bool need_comma
= false;
1558 if (ex_spec
== NULL
)
1560 if (TREE_PURPOSE (ex_spec
))
1562 pp_cxx_ws_string (pp
, "noexcept");
1563 pp_cxx_whitespace (pp
);
1564 pp_cxx_left_paren (pp
);
1565 if (DEFERRED_NOEXCEPT_SPEC_P (ex_spec
))
1566 pp_cxx_ws_string (pp
, "<uninstantiated>");
1568 pp
->expression (TREE_PURPOSE (ex_spec
));
1569 pp_cxx_right_paren (pp
);
1572 pp_cxx_ws_string (pp
, "throw");
1573 pp_cxx_left_paren (pp
);
1574 for (; ex_spec
&& TREE_VALUE (ex_spec
); ex_spec
= TREE_CHAIN (ex_spec
))
1576 tree type
= TREE_VALUE (ex_spec
);
1577 tree argpack
= NULL_TREE
;
1580 if (ARGUMENT_PACK_P (type
))
1582 argpack
= ARGUMENT_PACK_ARGS (type
);
1583 len
= TREE_VEC_LENGTH (argpack
);
1586 for (i
= 0; i
< len
; ++i
)
1589 type
= TREE_VEC_ELT (argpack
, i
);
1592 pp_cxx_separate_with (pp
, ',');
1599 pp_cxx_right_paren (pp
);
1602 /* direct-declarator:
1604 direct-declarator ( parameter-declaration-clause ) cv-qualifier-seq(opt)
1605 exception-specification(opt)
1606 direct-declaration [ constant-expression(opt) ]
1610 cxx_pretty_printer::direct_declarator (tree t
)
1612 switch (TREE_CODE (t
))
1620 pp_cxx_space_for_pointer_operator (this, TREE_TYPE (t
));
1622 if ((TREE_CODE (t
) == PARM_DECL
&& DECL_PACK_P (t
))
1623 || template_parameter_pack_p (t
))
1624 /* A function parameter pack or non-type template
1626 pp_cxx_ws_string (this, "...");
1628 id_expression (DECL_NAME (t
));
1630 abstract_declarator (TREE_TYPE (t
));
1634 pp_cxx_space_for_pointer_operator (this, TREE_TYPE (TREE_TYPE (t
)));
1636 pp_cxx_parameter_declaration_clause (this, t
);
1638 if (DECL_NONSTATIC_MEMBER_FUNCTION_P (t
))
1640 padding
= pp_before
;
1641 pp_cxx_cv_qualifier_seq (this, pp_cxx_implicit_parameter_type (t
));
1644 pp_cxx_exception_specification (this, TREE_TYPE (t
));
1649 case TEMPLATE_TYPE_PARM
:
1650 case TEMPLATE_PARM_INDEX
:
1651 case TEMPLATE_TEMPLATE_PARM
:
1655 c_pretty_printer::direct_declarator (t
);
1662 ptr-operator declarator */
1665 cxx_pretty_printer::declarator (tree t
)
1667 direct_declarator (t
);
1669 // Print a requires clause.
1671 if (tree ci
= get_constraints (t
))
1672 if (tree reqs
= CI_DECLARATOR_REQS (ci
))
1673 pp_cxx_requires_clause (this, reqs
);
1676 /* ctor-initializer:
1677 : mem-initializer-list
1679 mem-initializer-list:
1681 mem-initializer , mem-initializer-list
1684 mem-initializer-id ( expression-list(opt) )
1687 ::(opt) nested-name-specifier(opt) class-name
1691 pp_cxx_ctor_initializer (cxx_pretty_printer
*pp
, tree t
)
1693 t
= TREE_OPERAND (t
, 0);
1694 pp_cxx_whitespace (pp
);
1696 pp_cxx_whitespace (pp
);
1697 for (; t
; t
= TREE_CHAIN (t
))
1699 tree purpose
= TREE_PURPOSE (t
);
1700 bool is_pack
= PACK_EXPANSION_P (purpose
);
1703 pp
->primary_expression (PACK_EXPANSION_PATTERN (purpose
));
1705 pp
->primary_expression (purpose
);
1706 pp_cxx_call_argument_list (pp
, TREE_VALUE (t
));
1708 pp_cxx_ws_string (pp
, "...");
1710 pp_cxx_separate_with (pp
, ',');
1714 /* function-definition:
1715 decl-specifier-seq(opt) declarator ctor-initializer(opt) function-body
1716 decl-specifier-seq(opt) declarator function-try-block */
1719 pp_cxx_function_definition (cxx_pretty_printer
*pp
, tree t
)
1721 tree saved_scope
= pp
->enclosing_scope
;
1722 pp
->declaration_specifiers (t
);
1724 pp_needs_newline (pp
) = true;
1725 pp
->enclosing_scope
= DECL_CONTEXT (t
);
1726 if (DECL_SAVED_TREE (t
))
1727 pp
->statement (DECL_SAVED_TREE (t
));
1729 pp_cxx_semicolon (pp
);
1730 pp_newline_and_flush (pp
);
1731 pp
->enclosing_scope
= saved_scope
;
1734 /* abstract-declarator:
1735 ptr-operator abstract-declarator(opt)
1736 direct-abstract-declarator */
1739 cxx_pretty_printer::abstract_declarator (tree t
)
1741 if (TYPE_PTRMEM_P (t
))
1742 pp_cxx_right_paren (this);
1743 else if (INDIRECT_TYPE_P (t
))
1745 if (TREE_CODE (TREE_TYPE (t
)) == ARRAY_TYPE
1746 || TREE_CODE (TREE_TYPE (t
)) == FUNCTION_TYPE
)
1747 pp_cxx_right_paren (this);
1750 direct_abstract_declarator (t
);
1753 /* direct-abstract-declarator:
1754 direct-abstract-declarator(opt) ( parameter-declaration-clause )
1755 cv-qualifier-seq(opt) exception-specification(opt)
1756 direct-abstract-declarator(opt) [ constant-expression(opt) ]
1757 ( abstract-declarator ) */
1760 cxx_pretty_printer::direct_abstract_declarator (tree t
)
1762 switch (TREE_CODE (t
))
1764 case REFERENCE_TYPE
:
1765 abstract_declarator (t
);
1769 if (TYPE_PTRMEMFUNC_P (t
))
1770 direct_abstract_declarator (TYPE_PTRMEMFUNC_FN_TYPE (t
));
1775 pp_cxx_parameter_declaration_clause (this, t
);
1776 direct_abstract_declarator (TREE_TYPE (t
));
1777 if (TREE_CODE (t
) == METHOD_TYPE
)
1779 padding
= pp_before
;
1780 pp_cxx_cv_qualifier_seq (this, class_of_this_parm (t
));
1782 pp_cxx_exception_specification (this, t
);
1786 case TEMPLATE_TYPE_PARM
:
1787 case TEMPLATE_TEMPLATE_PARM
:
1788 case BOUND_TEMPLATE_TEMPLATE_PARM
:
1789 case UNBOUND_CLASS_TEMPLATE
:
1793 c_pretty_printer::direct_abstract_declarator (t
);
1799 type-specifier-seq abstract-declarator(opt) */
1802 cxx_pretty_printer::type_id (tree t
)
1804 pp_flags saved_flags
= flags
;
1805 flags
|= pp_c_flag_abstract
;
1807 switch (TREE_CODE (t
))
1814 case BOUND_TEMPLATE_TEMPLATE_PARM
:
1815 case UNBOUND_CLASS_TEMPLATE
:
1816 case TEMPLATE_TEMPLATE_PARM
:
1817 case TEMPLATE_TYPE_PARM
:
1818 case TEMPLATE_PARM_INDEX
:
1821 case UNDERLYING_TYPE
:
1823 case TEMPLATE_ID_EXPR
:
1824 pp_cxx_type_specifier_seq (this, t
);
1827 case TYPE_PACK_EXPANSION
:
1828 type_id (PACK_EXPANSION_PATTERN (t
));
1829 pp_cxx_ws_string (this, "...");
1833 c_pretty_printer::type_id (t
);
1837 flags
= saved_flags
;
1840 /* template-argument-list:
1841 template-argument ...(opt)
1842 template-argument-list, template-argument ...(opt)
1845 assignment-expression
1850 pp_cxx_template_argument_list (cxx_pretty_printer
*pp
, tree t
)
1853 bool need_comma
= false;
1857 for (i
= 0; i
< TREE_VEC_LENGTH (t
); ++i
)
1859 tree arg
= TREE_VEC_ELT (t
, i
);
1860 tree argpack
= NULL_TREE
;
1863 if (ARGUMENT_PACK_P (arg
))
1865 argpack
= ARGUMENT_PACK_ARGS (arg
);
1866 len
= TREE_VEC_LENGTH (argpack
);
1869 for (idx
= 0; idx
< len
; idx
++)
1872 arg
= TREE_VEC_ELT (argpack
, idx
);
1875 pp_cxx_separate_with (pp
, ',');
1879 if (TYPE_P (arg
) || (TREE_CODE (arg
) == TEMPLATE_DECL
1880 && TYPE_P (DECL_TEMPLATE_RESULT (arg
))))
1883 pp
->expression (arg
);
1890 pp_cxx_exception_declaration (cxx_pretty_printer
*pp
, tree t
)
1892 t
= DECL_EXPR_DECL (t
);
1893 pp_cxx_type_specifier_seq (pp
, t
);
1895 pp
->abstract_declarator (t
);
1903 cxx_pretty_printer::statement (tree t
)
1905 switch (TREE_CODE (t
))
1907 case CTOR_INITIALIZER
:
1908 pp_cxx_ctor_initializer (this, t
);
1912 pp_cxx_ws_string (this, "using");
1913 pp_cxx_ws_string (this, "namespace");
1914 if (DECL_CONTEXT (t
))
1915 pp_cxx_nested_name_specifier (this, DECL_CONTEXT (t
));
1916 pp_cxx_qualified_id (this, USING_STMT_NAMESPACE (t
));
1920 pp_cxx_ws_string (this, "using");
1921 pp_cxx_nested_name_specifier (this, USING_DECL_SCOPE (t
));
1922 pp_cxx_unqualified_id (this, DECL_NAME (t
));
1929 try compound-statement handler-seq */
1931 pp_maybe_newline_and_indent (this, 0);
1932 pp_cxx_ws_string (this, "try");
1933 pp_newline_and_indent (this, 3);
1934 statement (TRY_STMTS (t
));
1935 pp_newline_and_indent (this, -3);
1939 statement (TRY_HANDLERS (t
));
1944 handler handler-seq(opt)
1947 catch ( exception-declaration ) compound-statement
1949 exception-declaration:
1950 type-specifier-seq declarator
1951 type-specifier-seq abstract-declarator
1954 pp_cxx_ws_string (this, "catch");
1955 pp_cxx_left_paren (this);
1956 pp_cxx_exception_declaration (this, HANDLER_PARMS (t
));
1957 pp_cxx_right_paren (this);
1958 pp_indentation (this) += 3;
1959 pp_needs_newline (this) = true;
1960 statement (HANDLER_BODY (t
));
1961 pp_indentation (this) -= 3;
1962 pp_needs_newline (this) = true;
1965 /* selection-statement:
1966 if ( expression ) statement
1967 if ( expression ) statement else statement */
1969 pp_cxx_ws_string (this, "if");
1970 pp_cxx_whitespace (this);
1971 pp_cxx_left_paren (this);
1972 expression (IF_COND (t
));
1973 pp_cxx_right_paren (this);
1974 pp_newline_and_indent (this, 2);
1975 statement (THEN_CLAUSE (t
));
1976 pp_newline_and_indent (this, -2);
1977 if (ELSE_CLAUSE (t
))
1979 tree else_clause
= ELSE_CLAUSE (t
);
1980 pp_cxx_ws_string (this, "else");
1981 if (TREE_CODE (else_clause
) == IF_STMT
)
1982 pp_cxx_whitespace (this);
1984 pp_newline_and_indent (this, 2);
1985 statement (else_clause
);
1986 if (TREE_CODE (else_clause
) != IF_STMT
)
1987 pp_newline_and_indent (this, -2);
1992 pp_cxx_ws_string (this, "switch");
1994 pp_cxx_left_paren (this);
1995 expression (SWITCH_STMT_COND (t
));
1996 pp_cxx_right_paren (this);
1997 pp_indentation (this) += 3;
1998 pp_needs_newline (this) = true;
1999 statement (SWITCH_STMT_BODY (t
));
2000 pp_newline_and_indent (this, -3);
2003 /* iteration-statement:
2004 while ( expression ) statement
2005 do statement while ( expression ) ;
2006 for ( expression(opt) ; expression(opt) ; expression(opt) ) statement
2007 for ( declaration expression(opt) ; expression(opt) ) statement */
2009 pp_cxx_ws_string (this, "while");
2011 pp_cxx_left_paren (this);
2012 expression (WHILE_COND (t
));
2013 pp_cxx_right_paren (this);
2014 pp_newline_and_indent (this, 3);
2015 statement (WHILE_BODY (t
));
2016 pp_indentation (this) -= 3;
2017 pp_needs_newline (this) = true;
2021 pp_cxx_ws_string (this, "do");
2022 pp_newline_and_indent (this, 3);
2023 statement (DO_BODY (t
));
2024 pp_newline_and_indent (this, -3);
2025 pp_cxx_ws_string (this, "while");
2027 pp_cxx_left_paren (this);
2028 expression (DO_COND (t
));
2029 pp_cxx_right_paren (this);
2030 pp_cxx_semicolon (this);
2031 pp_needs_newline (this) = true;
2035 pp_cxx_ws_string (this, "for");
2037 pp_cxx_left_paren (this);
2038 if (FOR_INIT_STMT (t
))
2039 statement (FOR_INIT_STMT (t
));
2041 pp_cxx_semicolon (this);
2042 pp_needs_newline (this) = false;
2043 pp_cxx_whitespace (this);
2045 expression (FOR_COND (t
));
2046 pp_cxx_semicolon (this);
2047 pp_needs_newline (this) = false;
2048 pp_cxx_whitespace (this);
2050 expression (FOR_EXPR (t
));
2051 pp_cxx_right_paren (this);
2052 pp_newline_and_indent (this, 3);
2053 statement (FOR_BODY (t
));
2054 pp_indentation (this) -= 3;
2055 pp_needs_newline (this) = true;
2058 case RANGE_FOR_STMT
:
2059 pp_cxx_ws_string (this, "for");
2061 pp_cxx_left_paren (this);
2062 if (RANGE_FOR_INIT_STMT (t
))
2064 statement (RANGE_FOR_INIT_STMT (t
));
2065 pp_needs_newline (this) = false;
2066 pp_cxx_whitespace (this);
2068 statement (RANGE_FOR_DECL (t
));
2070 pp_needs_newline (this) = false;
2073 statement (RANGE_FOR_EXPR (t
));
2074 pp_cxx_right_paren (this);
2075 pp_newline_and_indent (this, 3);
2076 statement (FOR_BODY (t
));
2077 pp_indentation (this) -= 3;
2078 pp_needs_newline (this) = true;
2084 return expression(opt) ; */
2087 pp_string (this, TREE_CODE (t
) == BREAK_STMT
? "break" : "continue");
2088 pp_cxx_semicolon (this);
2089 pp_needs_newline (this) = true;
2092 /* expression-statement:
2093 expression(opt) ; */
2095 expression (EXPR_STMT_EXPR (t
));
2096 pp_cxx_semicolon (this);
2097 pp_needs_newline (this) = true;
2101 pp_cxx_ws_string (this, "try");
2102 pp_newline_and_indent (this, 2);
2103 statement (CLEANUP_BODY (t
));
2104 pp_newline_and_indent (this, -2);
2105 pp_cxx_ws_string (this, CLEANUP_EH_ONLY (t
) ? "catch" : "finally");
2106 pp_newline_and_indent (this, 2);
2107 statement (CLEANUP_EXPR (t
));
2108 pp_newline_and_indent (this, -2);
2116 c_pretty_printer::statement (t
);
2121 /* original-namespace-definition:
2122 namespace identifier { namespace-body }
2124 As an edge case, we also handle unnamed namespace definition here. */
2127 pp_cxx_original_namespace_definition (cxx_pretty_printer
*pp
, tree t
)
2129 pp_cxx_ws_string (pp
, "namespace");
2130 if (DECL_CONTEXT (t
))
2131 pp_cxx_nested_name_specifier (pp
, DECL_CONTEXT (t
));
2133 pp_cxx_unqualified_id (pp
, t
);
2134 pp_cxx_whitespace (pp
);
2135 pp_cxx_left_brace (pp
);
2136 /* We do not print the namespace-body. */
2137 pp_cxx_whitespace (pp
);
2138 pp_cxx_right_brace (pp
);
2144 namespace-alias-definition:
2145 namespace identifier = qualified-namespace-specifier ;
2147 qualified-namespace-specifier:
2148 ::(opt) nested-name-specifier(opt) namespace-name */
2151 pp_cxx_namespace_alias_definition (cxx_pretty_printer
*pp
, tree t
)
2153 pp_cxx_ws_string (pp
, "namespace");
2154 if (DECL_CONTEXT (t
))
2155 pp_cxx_nested_name_specifier (pp
, DECL_CONTEXT (t
));
2156 pp_cxx_unqualified_id (pp
, t
);
2157 pp_cxx_whitespace (pp
);
2159 pp_cxx_whitespace (pp
);
2160 if (DECL_CONTEXT (DECL_NAMESPACE_ALIAS (t
)))
2161 pp_cxx_nested_name_specifier (pp
,
2162 DECL_CONTEXT (DECL_NAMESPACE_ALIAS (t
)));
2163 pp_cxx_qualified_id (pp
, DECL_NAMESPACE_ALIAS (t
));
2164 pp_cxx_semicolon (pp
);
2167 /* simple-declaration:
2168 decl-specifier-seq(opt) init-declarator-list(opt) */
2171 pp_cxx_simple_declaration (cxx_pretty_printer
*pp
, tree t
)
2173 pp
->declaration_specifiers (t
);
2174 pp_cxx_init_declarator (pp
, t
);
2175 pp_cxx_semicolon (pp
);
2176 pp_needs_newline (pp
) = true;
2180 template-parameter-list:
2182 template-parameter-list , template-parameter */
2185 pp_cxx_template_parameter_list (cxx_pretty_printer
*pp
, tree t
)
2187 const int n
= TREE_VEC_LENGTH (t
);
2189 for (i
= 0; i
< n
; ++i
)
2192 pp_cxx_separate_with (pp
, ',');
2193 pp_cxx_template_parameter (pp
, TREE_VEC_ELT (t
, i
));
2197 /* template-parameter:
2199 parameter-declaration
2202 class ...(opt) identifier(opt)
2203 class identifier(opt) = type-id
2204 typename identifier(opt)
2205 typename ...(opt) identifier(opt) = type-id
2206 template < template-parameter-list > class ...(opt) identifier(opt)
2207 template < template-parameter-list > class identifier(opt) = template-name */
2210 pp_cxx_template_parameter (cxx_pretty_printer
*pp
, tree t
)
2212 tree parameter
= TREE_VALUE (t
);
2213 switch (TREE_CODE (parameter
))
2216 pp_cxx_ws_string (pp
, "class");
2217 if (TEMPLATE_TYPE_PARAMETER_PACK (TREE_TYPE (t
)))
2218 pp_cxx_ws_string (pp
, "...");
2219 if (DECL_NAME (parameter
))
2220 pp_cxx_tree_identifier (pp
, DECL_NAME (parameter
));
2221 /* FIXME: Check if we should print also default argument. */
2225 pp_cxx_parameter_declaration (pp
, parameter
);
2232 pp_unsupported_tree (pp
, t
);
2237 /* Pretty-print a template parameter in the canonical form
2238 "template-parameter-<level>-<position in parameter list>". */
2241 pp_cxx_canonical_template_parameter (cxx_pretty_printer
*pp
, tree parm
)
2243 const enum tree_code code
= TREE_CODE (parm
);
2245 /* Brings type template parameters to the canonical forms. */
2246 if (code
== TEMPLATE_TYPE_PARM
|| code
== TEMPLATE_TEMPLATE_PARM
2247 || code
== BOUND_TEMPLATE_TEMPLATE_PARM
)
2248 parm
= TEMPLATE_TYPE_PARM_INDEX (parm
);
2250 pp_cxx_begin_template_argument_list (pp
);
2251 pp
->translate_string ("template-parameter-");
2252 pp_wide_integer (pp
, TEMPLATE_PARM_LEVEL (parm
));
2254 pp_wide_integer (pp
, TEMPLATE_PARM_IDX (parm
) + 1);
2255 pp_cxx_end_template_argument_list (pp
);
2258 /* Print a constrained-type-specifier. */
2261 pp_cxx_constrained_type_spec (cxx_pretty_printer
*pp
, tree c
)
2264 if (c
== error_mark_node
)
2266 pp_cxx_ws_string(pp
, "<unsatisfied-constrained-placeholder>");
2269 placeholder_extract_concept_and_args (c
, t
, a
);
2270 pp
->id_expression (t
);
2271 if (TREE_VEC_LENGTH (a
) > 1)
2273 pp_cxx_begin_template_argument_list (pp
);
2274 tree args
= make_tree_vec (TREE_VEC_LENGTH (a
) - 1);
2275 for (int i
= TREE_VEC_LENGTH (a
) - 1; i
> 0; --i
)
2276 TREE_VEC_ELT (args
, i
-1) = TREE_VEC_ELT (a
, i
);
2277 pp_cxx_template_argument_list (pp
, args
);
2279 pp_cxx_end_template_argument_list (pp
);
2284 template-declaration:
2285 export(opt) template < template-parameter-list > declaration
2289 template-declaration:
2290 export(opt) template < template-parameter-list >
2291 requires-clause(opt) declaration */
2294 pp_cxx_template_declaration (cxx_pretty_printer
*pp
, tree t
)
2296 tree tmpl
= most_general_template (t
);
2299 pp_maybe_newline_and_indent (pp
, 0);
2300 for (level
= DECL_TEMPLATE_PARMS (tmpl
); level
; level
= TREE_CHAIN (level
))
2302 pp_cxx_ws_string (pp
, "template");
2303 pp_cxx_begin_template_argument_list (pp
);
2304 pp_cxx_template_parameter_list (pp
, TREE_VALUE (level
));
2305 pp_cxx_end_template_argument_list (pp
);
2306 pp_newline_and_indent (pp
, 3);
2310 if (tree ci
= get_constraints (t
))
2311 if (tree reqs
= CI_TEMPLATE_REQS (ci
))
2313 pp_cxx_requires_clause (pp
, reqs
);
2314 pp_newline_and_indent (pp
, 6);
2317 if (TREE_CODE (t
) == FUNCTION_DECL
&& DECL_SAVED_TREE (t
))
2318 pp_cxx_function_definition (pp
, t
);
2320 pp_cxx_simple_declaration (pp
, t
);
2324 pp_cxx_explicit_specialization (cxx_pretty_printer
*pp
, tree t
)
2326 pp_unsupported_tree (pp
, t
);
2330 pp_cxx_explicit_instantiation (cxx_pretty_printer
*pp
, tree t
)
2332 pp_unsupported_tree (pp
, t
);
2339 template-declaration
2340 explicit-instantiation
2341 explicit-specialization
2342 linkage-specification
2343 namespace-definition
2348 namespace-alias-definition
2351 static_assert-declaration */
2353 cxx_pretty_printer::declaration (tree t
)
2355 if (TREE_CODE (t
) == STATIC_ASSERT
)
2357 pp_cxx_ws_string (this, "static_assert");
2358 pp_cxx_left_paren (this);
2359 expression (STATIC_ASSERT_CONDITION (t
));
2360 pp_cxx_separate_with (this, ',');
2361 expression (STATIC_ASSERT_MESSAGE (t
));
2362 pp_cxx_right_paren (this);
2364 else if (!DECL_LANG_SPECIFIC (t
))
2365 pp_cxx_simple_declaration (this, t
);
2366 else if (DECL_USE_TEMPLATE (t
))
2367 switch (DECL_USE_TEMPLATE (t
))
2370 pp_cxx_template_declaration (this, t
);
2374 pp_cxx_explicit_specialization (this, t
);
2378 pp_cxx_explicit_instantiation (this, t
);
2384 else switch (TREE_CODE (t
))
2388 pp_cxx_simple_declaration (this, t
);
2392 if (DECL_SAVED_TREE (t
))
2393 pp_cxx_function_definition (this, t
);
2395 pp_cxx_simple_declaration (this, t
);
2398 case NAMESPACE_DECL
:
2399 if (DECL_NAMESPACE_ALIAS (t
))
2400 pp_cxx_namespace_alias_definition (this, t
);
2402 pp_cxx_original_namespace_definition (this, t
);
2406 pp_unsupported_tree (this, t
);
2412 pp_cxx_typeid_expression (cxx_pretty_printer
*pp
, tree t
)
2414 t
= TREE_OPERAND (t
, 0);
2415 pp_cxx_ws_string (pp
, "typeid");
2416 pp_cxx_left_paren (pp
);
2421 pp_cxx_right_paren (pp
);
2425 pp_cxx_va_arg_expression (cxx_pretty_printer
*pp
, tree t
)
2427 pp_cxx_ws_string (pp
, "va_arg");
2428 pp_cxx_left_paren (pp
);
2429 pp
->assignment_expression (TREE_OPERAND (t
, 0));
2430 pp_cxx_separate_with (pp
, ',');
2431 pp
->type_id (TREE_TYPE (t
));
2432 pp_cxx_right_paren (pp
);
2436 pp_cxx_offsetof_expression_1 (cxx_pretty_printer
*pp
, tree t
)
2438 switch (TREE_CODE (t
))
2441 if (TREE_CODE (TREE_OPERAND (t
, 0)) == STATIC_CAST_EXPR
2442 && INDIRECT_TYPE_P (TREE_TYPE (TREE_OPERAND (t
, 0))))
2444 pp
->type_id (TREE_TYPE (TREE_TYPE (TREE_OPERAND (t
, 0))));
2445 pp_cxx_separate_with (pp
, ',');
2450 if (!pp_cxx_offsetof_expression_1 (pp
, TREE_OPERAND (t
, 0)))
2452 if (TREE_CODE (TREE_OPERAND (t
, 0)) != ARROW_EXPR
)
2454 pp
->expression (TREE_OPERAND (t
, 1));
2457 if (!pp_cxx_offsetof_expression_1 (pp
, TREE_OPERAND (t
, 0)))
2459 pp_left_bracket (pp
);
2460 pp
->expression (TREE_OPERAND (t
, 1));
2461 pp_right_bracket (pp
);
2469 pp_cxx_offsetof_expression (cxx_pretty_printer
*pp
, tree t
)
2471 pp_cxx_ws_string (pp
, "offsetof");
2472 pp_cxx_left_paren (pp
);
2473 if (!pp_cxx_offsetof_expression_1 (pp
, TREE_OPERAND (t
, 0)))
2474 pp
->expression (TREE_OPERAND (t
, 0));
2475 pp_cxx_right_paren (pp
);
2479 pp_cxx_addressof_expression (cxx_pretty_printer
*pp
, tree t
)
2481 pp_cxx_ws_string (pp
, "__builtin_addressof");
2482 pp_cxx_left_paren (pp
);
2483 pp
->expression (TREE_OPERAND (t
, 0));
2484 pp_cxx_right_paren (pp
);
2488 get_fold_operator (tree t
)
2490 int op
= int_cst_value (FOLD_EXPR_OP (t
));
2491 if (FOLD_EXPR_MODIFY_P (t
))
2495 case NOP_EXPR
: return "=";
2496 case PLUS_EXPR
: return "+=";
2497 case MINUS_EXPR
: return "-=";
2498 case MULT_EXPR
: return "*=";
2499 case TRUNC_DIV_EXPR
: return "/=";
2500 case TRUNC_MOD_EXPR
: return "%=";
2501 case BIT_XOR_EXPR
: return "^=";
2502 case BIT_AND_EXPR
: return "&=";
2503 case BIT_IOR_EXPR
: return "|=";
2504 case LSHIFT_EXPR
: return "<<=";
2505 case RSHIFT_EXPR
: return ">>=";
2506 default: gcc_unreachable ();
2513 case PLUS_EXPR
: return "+";
2514 case MINUS_EXPR
: return "-";
2515 case MULT_EXPR
: return "*";
2516 case TRUNC_DIV_EXPR
: return "/";
2517 case TRUNC_MOD_EXPR
: return "%";
2518 case BIT_XOR_EXPR
: return "^";
2519 case BIT_AND_EXPR
: return "&";
2520 case BIT_IOR_EXPR
: return "|";
2521 case LSHIFT_EXPR
: return "<<";
2522 case RSHIFT_EXPR
: return ">>";
2523 case EQ_EXPR
: return "==";
2524 case NE_EXPR
: return "!=";
2525 case LT_EXPR
: return "<";
2526 case GT_EXPR
: return ">";
2527 case LE_EXPR
: return "<=";
2528 case GE_EXPR
: return ">=";
2529 case TRUTH_ANDIF_EXPR
: return "&&";
2530 case TRUTH_ORIF_EXPR
: return "||";
2531 case MEMBER_REF
: return "->*";
2532 case DOTSTAR_EXPR
: return ".*";
2533 case OFFSET_REF
: return ".*";
2534 default: return ","; /* FIXME: Not the right default. */
2540 pp_cxx_unary_left_fold_expression (cxx_pretty_printer
*pp
, tree t
)
2542 char const* op
= get_fold_operator (t
);
2543 tree expr
= PACK_EXPANSION_PATTERN (FOLD_EXPR_PACK (t
));
2544 pp_cxx_left_paren (pp
);
2545 pp_cxx_ws_string (pp
, "...");
2546 pp_cxx_ws_string (pp
, op
);
2547 pp
->expression (expr
);
2548 pp_cxx_right_paren (pp
);
2552 pp_cxx_unary_right_fold_expression (cxx_pretty_printer
*pp
, tree t
)
2554 char const* op
= get_fold_operator (t
);
2555 tree expr
= PACK_EXPANSION_PATTERN (FOLD_EXPR_PACK (t
));
2556 pp_cxx_left_paren (pp
);
2557 pp
->expression (expr
);
2559 pp_cxx_ws_string (pp
, op
);
2560 pp_cxx_ws_string (pp
, "...");
2561 pp_cxx_right_paren (pp
);
2565 pp_cxx_binary_fold_expression (cxx_pretty_printer
*pp
, tree t
)
2567 char const* op
= get_fold_operator (t
);
2568 tree t1
= TREE_OPERAND (t
, 1);
2569 tree t2
= TREE_OPERAND (t
, 2);
2570 if (t1
== FOLD_EXPR_PACK (t
))
2571 t1
= PACK_EXPANSION_PATTERN (t1
);
2573 t2
= PACK_EXPANSION_PATTERN (t2
);
2574 pp_cxx_left_paren (pp
);
2575 pp
->expression (t1
);
2576 pp_cxx_ws_string (pp
, op
);
2577 pp_cxx_ws_string (pp
, "...");
2578 pp_cxx_ws_string (pp
, op
);
2579 pp
->expression (t2
);
2580 pp_cxx_right_paren (pp
);
2584 pp_cxx_trait_expression (cxx_pretty_printer
*pp
, tree t
)
2586 cp_trait_kind kind
= TRAIT_EXPR_KIND (t
);
2590 case CPTK_HAS_NOTHROW_ASSIGN
:
2591 pp_cxx_ws_string (pp
, "__has_nothrow_assign");
2593 case CPTK_HAS_TRIVIAL_ASSIGN
:
2594 pp_cxx_ws_string (pp
, "__has_trivial_assign");
2596 case CPTK_HAS_NOTHROW_CONSTRUCTOR
:
2597 pp_cxx_ws_string (pp
, "__has_nothrow_constructor");
2599 case CPTK_HAS_TRIVIAL_CONSTRUCTOR
:
2600 pp_cxx_ws_string (pp
, "__has_trivial_constructor");
2602 case CPTK_HAS_NOTHROW_COPY
:
2603 pp_cxx_ws_string (pp
, "__has_nothrow_copy");
2605 case CPTK_HAS_TRIVIAL_COPY
:
2606 pp_cxx_ws_string (pp
, "__has_trivial_copy");
2608 case CPTK_HAS_TRIVIAL_DESTRUCTOR
:
2609 pp_cxx_ws_string (pp
, "__has_trivial_destructor");
2611 case CPTK_HAS_UNIQUE_OBJ_REPRESENTATIONS
:
2612 pp_cxx_ws_string (pp
, "__has_unique_object_representations");
2614 case CPTK_HAS_VIRTUAL_DESTRUCTOR
:
2615 pp_cxx_ws_string (pp
, "__has_virtual_destructor");
2617 case CPTK_IS_ABSTRACT
:
2618 pp_cxx_ws_string (pp
, "__is_abstract");
2620 case CPTK_IS_AGGREGATE
:
2621 pp_cxx_ws_string (pp
, "__is_aggregate");
2623 case CPTK_IS_BASE_OF
:
2624 pp_cxx_ws_string (pp
, "__is_base_of");
2627 pp_cxx_ws_string (pp
, "__is_class");
2630 pp_cxx_ws_string (pp
, "__is_empty");
2633 pp_cxx_ws_string (pp
, "__is_enum");
2636 pp_cxx_ws_string (pp
, "__is_final");
2639 pp_cxx_ws_string (pp
, "__is_pod");
2641 case CPTK_IS_POLYMORPHIC
:
2642 pp_cxx_ws_string (pp
, "__is_polymorphic");
2644 case CPTK_IS_SAME_AS
:
2645 pp_cxx_ws_string (pp
, "__is_same_as");
2647 case CPTK_IS_STD_LAYOUT
:
2648 pp_cxx_ws_string (pp
, "__is_std_layout");
2650 case CPTK_IS_TRIVIAL
:
2651 pp_cxx_ws_string (pp
, "__is_trivial");
2653 case CPTK_IS_TRIVIALLY_ASSIGNABLE
:
2654 pp_cxx_ws_string (pp
, "__is_trivially_assignable");
2656 case CPTK_IS_TRIVIALLY_CONSTRUCTIBLE
:
2657 pp_cxx_ws_string (pp
, "__is_trivially_constructible");
2659 case CPTK_IS_TRIVIALLY_COPYABLE
:
2660 pp_cxx_ws_string (pp
, "__is_trivially_copyable");
2663 pp_cxx_ws_string (pp
, "__is_union");
2665 case CPTK_IS_LITERAL_TYPE
:
2666 pp_cxx_ws_string (pp
, "__is_literal_type");
2668 case CPTK_IS_ASSIGNABLE
:
2669 pp_cxx_ws_string (pp
, "__is_assignable");
2671 case CPTK_IS_CONSTRUCTIBLE
:
2672 pp_cxx_ws_string (pp
, "__is_constructible");
2679 pp_cxx_left_paren (pp
);
2680 pp
->type_id (TRAIT_EXPR_TYPE1 (t
));
2682 if (kind
== CPTK_IS_BASE_OF
|| kind
== CPTK_IS_SAME_AS
)
2684 pp_cxx_separate_with (pp
, ',');
2685 pp
->type_id (TRAIT_EXPR_TYPE2 (t
));
2688 pp_cxx_right_paren (pp
);
2692 // 'requires' logical-or-expression
2694 pp_cxx_requires_clause (cxx_pretty_printer
*pp
, tree t
)
2698 pp
->padding
= pp_before
;
2699 pp_cxx_ws_string (pp
, "requires");
2706 compound-requirement
2708 nested-requirement */
2710 pp_cxx_requirement (cxx_pretty_printer
*pp
, tree t
)
2712 switch (TREE_CODE (t
))
2715 pp_cxx_simple_requirement (pp
, t
);
2719 pp_cxx_type_requirement (pp
, t
);
2723 pp_cxx_compound_requirement (pp
, t
);
2727 pp_cxx_nested_requirement (pp
, t
);
2735 // requirement-list:
2737 // requirement-list ';' requirement[opt]
2740 pp_cxx_requirement_list (cxx_pretty_printer
*pp
, tree t
)
2742 for (; t
; t
= TREE_CHAIN (t
))
2743 pp_cxx_requirement (pp
, TREE_VALUE (t
));
2746 // requirement-body:
2747 // '{' requirement-list '}'
2749 pp_cxx_requirement_body (cxx_pretty_printer
*pp
, tree t
)
2751 pp_cxx_left_brace (pp
);
2752 pp_cxx_requirement_list (pp
, t
);
2753 pp_cxx_right_brace (pp
);
2756 // requires-expression:
2757 // 'requires' requirement-parameter-list requirement-body
2759 pp_cxx_requires_expr (cxx_pretty_printer
*pp
, tree t
)
2761 pp_string (pp
, "requires");
2762 if (tree parms
= TREE_OPERAND (t
, 0))
2764 pp_cxx_parameter_declaration_clause (pp
, parms
);
2765 pp_cxx_whitespace (pp
);
2767 pp_cxx_requirement_body (pp
, TREE_OPERAND (t
, 1));
2770 /* simple-requirement:
2773 pp_cxx_simple_requirement (cxx_pretty_printer
*pp
, tree t
)
2775 pp
->expression (TREE_OPERAND (t
, 0));
2776 pp_cxx_semicolon (pp
);
2779 /* type-requirement:
2780 typename type-name ';' */
2782 pp_cxx_type_requirement (cxx_pretty_printer
*pp
, tree t
)
2784 pp
->type_id (TREE_OPERAND (t
, 0));
2785 pp_cxx_semicolon (pp
);
2788 /* compound-requirement:
2789 '{' expression '}' 'noexcept' [opt] trailing-return-type [opt] */
2791 pp_cxx_compound_requirement (cxx_pretty_printer
*pp
, tree t
)
2793 pp_cxx_left_brace (pp
);
2794 pp
->expression (TREE_OPERAND (t
, 0));
2795 pp_cxx_right_brace (pp
);
2797 if (COMPOUND_REQ_NOEXCEPT_P (t
))
2798 pp_cxx_ws_string (pp
, "noexcept");
2800 if (tree type
= TREE_OPERAND (t
, 1))
2802 pp_cxx_ws_string (pp
, "->");
2805 pp_cxx_semicolon (pp
);
2808 /* nested requirement:
2809 'requires' constraint-expression */
2811 pp_cxx_nested_requirement (cxx_pretty_printer
*pp
, tree t
)
2813 pp_cxx_ws_string (pp
, "requires");
2814 pp
->expression (TREE_OPERAND (t
, 0));
2815 pp_cxx_semicolon (pp
);
2819 pp_cxx_predicate_constraint (cxx_pretty_printer
*pp
, tree t
)
2821 pp
->expression (TREE_OPERAND (t
, 0));
2825 pp_cxx_check_constraint (cxx_pretty_printer
*pp
, tree t
)
2827 tree decl
= CHECK_CONSTR_CONCEPT (t
);
2828 tree tmpl
= DECL_TI_TEMPLATE (decl
);
2829 tree args
= CHECK_CONSTR_ARGS (t
);
2830 tree id
= build_nt (TEMPLATE_ID_EXPR
, tmpl
, args
);
2833 pp
->expression (id
);
2834 else if (TREE_CODE (decl
) == FUNCTION_DECL
)
2836 tree call
= build_vl_exp (CALL_EXPR
, 2);
2837 TREE_OPERAND (call
, 0) = integer_two_node
;
2838 TREE_OPERAND (call
, 1) = id
;
2839 pp
->expression (call
);
2846 pp_cxx_expression_constraint (cxx_pretty_printer
*pp
, tree t
)
2848 pp_string (pp
, "<valid-expression ");
2849 pp_cxx_left_paren (pp
);
2850 pp
->expression (TREE_OPERAND (t
, 0));
2851 pp_cxx_right_paren (pp
);
2852 pp_string (pp
, ">");
2856 pp_cxx_type_constraint (cxx_pretty_printer
*pp
, tree t
)
2858 pp_string (pp
, "<valid-type ");
2859 pp
->type_id (TREE_OPERAND (t
, 0));
2860 pp_string (pp
, ">");
2864 pp_cxx_implicit_conversion_constraint (cxx_pretty_printer
*pp
, tree t
)
2866 pp_string (pp
, "<implicitly-conversion ");
2867 pp_cxx_left_paren (pp
);
2868 pp
->expression (ICONV_CONSTR_EXPR (t
));
2869 pp_cxx_right_paren (pp
);
2870 pp_cxx_ws_string (pp
, "to");
2871 pp
->type_id (ICONV_CONSTR_TYPE (t
));
2872 pp_string (pp
, ">");
2876 pp_cxx_argument_deduction_constraint (cxx_pretty_printer
*pp
, tree t
)
2878 pp_string (pp
, "<argument-deduction ");
2879 pp_cxx_left_paren (pp
);
2880 pp
->expression (DEDUCT_CONSTR_EXPR (t
));
2881 pp_cxx_right_paren (pp
);
2882 pp_cxx_ws_string (pp
, "as");
2883 pp
->expression (DEDUCT_CONSTR_PATTERN (t
));
2884 pp_string (pp
, ">");
2888 pp_cxx_exception_constraint (cxx_pretty_printer
*pp
, tree t
)
2890 pp_cxx_ws_string (pp
, "noexcept");
2891 pp_cxx_whitespace (pp
);
2892 pp_cxx_left_paren (pp
);
2893 pp
->expression (TREE_OPERAND (t
, 0));
2894 pp_cxx_right_paren (pp
);
2898 pp_cxx_parameterized_constraint (cxx_pretty_printer
*pp
, tree t
)
2901 pp_string (pp
, "<requires ");
2902 if (tree parms
= PARM_CONSTR_PARMS (t
))
2904 pp_cxx_parameter_declaration_clause (pp
, parms
);
2905 pp_cxx_whitespace (pp
);
2907 pp_cxx_constraint (pp
, PARM_CONSTR_OPERAND (t
));
2908 pp_string (pp
, ">");
2912 pp_cxx_conjunction (cxx_pretty_printer
*pp
, tree t
)
2914 pp_cxx_constraint (pp
, TREE_OPERAND (t
, 0));
2915 pp_string (pp
, " and ");
2916 pp_cxx_constraint (pp
, TREE_OPERAND (t
, 1));
2920 pp_cxx_disjunction (cxx_pretty_printer
*pp
, tree t
)
2922 pp_cxx_constraint (pp
, TREE_OPERAND (t
, 0));
2923 pp_string (pp
, " or ");
2924 pp_cxx_constraint (pp
, TREE_OPERAND (t
, 1));
2928 pp_cxx_constraint (cxx_pretty_printer
*pp
, tree t
)
2930 if (t
== error_mark_node
)
2931 return pp
->expression (t
);
2933 switch (TREE_CODE (t
))
2936 pp_cxx_predicate_constraint (pp
, t
);
2940 pp_cxx_check_constraint (pp
, t
);
2944 pp_cxx_expression_constraint (pp
, t
);
2948 pp_cxx_type_constraint (pp
, t
);
2952 pp_cxx_implicit_conversion_constraint (pp
, t
);
2956 pp_cxx_argument_deduction_constraint (pp
, t
);
2960 pp_cxx_exception_constraint (pp
, t
);
2964 pp_cxx_parameterized_constraint (pp
, t
);
2968 pp_cxx_conjunction (pp
, t
);
2972 pp_cxx_disjunction (pp
, t
);
2975 case EXPR_PACK_EXPANSION
:
2976 pp
->expression (TREE_OPERAND (t
, 0));
2986 typedef c_pretty_print_fn pp_fun
;
2988 /* Initialization of a C++ pretty-printer object. */
2990 cxx_pretty_printer::cxx_pretty_printer ()
2991 : c_pretty_printer (),
2992 enclosing_scope (global_namespace
)
2994 type_specifier_seq
= (pp_fun
) pp_cxx_type_specifier_seq
;
2995 parameter_list
= (pp_fun
) pp_cxx_parameter_declaration_clause
;