1/* Classic text-based output of diagnostics.
2 Copyright (C) 2023-2026 Free Software Foundation, Inc.
3 Contributed by David Malcolm <dmalcolm@redhat.com>.
4
5This file is part of GCC.
6
7GCC is free software; you can redistribute it and/or modify it under
8the terms of the GNU General Public License as published by the Free
9Software Foundation; either version 3, or (at your option) any later
10version.
11
12GCC is distributed in the hope that it will be useful, but WITHOUT ANY
13WARRANTY; without even the implied warranty of MERCHANTABILITY or
14FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
15for more details.
16
17You should have received a copy of the GNU General Public License
18along with GCC; see the file COPYING3. If not see
19<http://www.gnu.org/licenses/>. */
20
21#ifndef GCC_DIAGNOSTICS_TEXT_SINK_H
22#define GCC_DIAGNOSTICS_TEXT_SINK_H
23
24#include "diagnostics/sink.h"
25
26namespace diagnostics {
27
28/* Subclass of diagnostics::sink for classic text-based output
29 to stderr.
30
31 Uses diagnostics::context.m_text_callbacks to provide client-specific
32 textual output (e.g. include paths, macro expansions, etc). */
33
34class text_sink : public sink
35{
36public:
37 text_sink (context &dc,
38 source_printing_options *source_printing = nullptr,
39 bool follows_reference_printer = false)
40 : sink (dc),
41 m_saved_output_buffer (nullptr),
42 m_column_policy (dc),
43 m_last_module (nullptr),
44 m_includes_seen (nullptr),
45 m_source_printing (source_printing
46 ? *source_printing
47 : dc.get_source_printing_options ()),
48 m_follows_reference_printer (follows_reference_printer),
49 m_show_nesting (false),
50 m_show_nesting_levels (false)
51 {}
52 ~text_sink ();
53
54 text_sink *dyn_cast_text_sink () final override { return this; }
55
56 void dump_kind (FILE *out) const override
57 {
58 fprintf (stream: out, format: "text_sink");
59 }
60 void dump (FILE *out, int indent) const override;
61
62 std::unique_ptr<per_sink_buffer>
63 make_per_sink_buffer () final override;
64 void set_buffer (per_sink_buffer *) final override;
65
66 void on_begin_group () override {}
67 void on_end_group () override {}
68 void on_report_diagnostic (const diagnostic_info &,
69 enum kind orig_diag_kind) override;
70 void on_report_verbatim (text_info &) final override;
71 void on_diagram (const diagram &d) override;
72 void after_diagnostic (const diagnostic_info &) override;
73 bool machine_readable_stderr_p () const final override
74 {
75 return false;
76 }
77 bool follows_reference_printer_p () const final override;
78
79 void update_printer () override;
80
81 void
82 report_global_digraph (const lazily_created<digraphs::digraph> &)
83 final override
84 {
85 // no-op for text
86 }
87
88 void
89 report_digraph_for_logical_location (const lazily_created<digraphs::digraph> &,
90 logical_locations::key) final override
91 {
92 // no-op for text
93 }
94
95 /* Helpers for writing lang-specific starters/finalizers for text output. */
96 char *build_prefix (const diagnostic_info &) const;
97 void report_current_module (location_t where);
98 void append_note (location_t location,
99 const char * gmsgid, ...) ATTRIBUTE_GCC_DIAG(3,4);
100
101
102 char *file_name_as_prefix (const char *) const;
103
104 char *build_indent_prefix (bool with_bullet) const;
105
106 void print_path (const paths::path &path);
107
108 bool show_column_p () const { return get_context ().m_show_column; }
109
110 const column_policy &get_column_policy () const
111 {
112 return m_column_policy;
113 }
114 location_print_policy get_location_print_policy () const;
115
116 bool show_nesting_p () const { return m_show_nesting; }
117 bool show_locations_in_nesting_p () const
118 {
119 return m_show_locations_in_nesting;
120 }
121
122 void set_show_nesting (bool show_nesting) { m_show_nesting = show_nesting; }
123 void set_show_locations_in_nesting (bool val)
124 {
125 m_show_locations_in_nesting = val;
126 }
127 void set_show_nesting_levels (bool show_nesting_levels)
128 {
129 m_show_nesting_levels = show_nesting_levels;
130 }
131
132 label_text get_location_text (const expanded_location &s) const;
133
134 source_printing_options &get_source_printing_options ()
135 {
136 return m_source_printing;
137 }
138 const source_printing_options &get_source_printing_options () const
139 {
140 return m_source_printing;
141 }
142
143 static const char *maybe_line_and_column (int line, int col);
144
145protected:
146 void print_any_cwe (const diagnostic_info &diagnostic);
147 void print_any_rules (const diagnostic_info &diagnostic);
148 void print_option_information (const diagnostic_info &diagnostic,
149 enum kind orig_diag_kind);
150
151 bool includes_seen_p (const line_map_ordinary *map);
152
153 /* For handling diagnostics::buffer. */
154 output_buffer *m_saved_output_buffer;
155
156 column_policy m_column_policy;
157
158 /* Used to detect when the input file stack has changed since last
159 described. */
160 const line_map_ordinary *m_last_module;
161
162 /* Include files that report_current_module has already listed the
163 include path for. */
164 hash_set<location_t, false, location_hash> *m_includes_seen;
165
166 source_printing_options &m_source_printing;
167
168 /* If true, this is the initial default text output format created
169 when the diagnostics::context was created, and, in particular, before
170 initializations of color and m_url_format. Hence this should follow
171 the dc's reference printer for these.
172 If false, this text output was created after the dc was created, and
173 thus tracks its own values for color and m_url_format. */
174 bool m_follows_reference_printer;
175
176 /* If true, then use indentation to show the nesting structure of
177 nested diagnostics, and print locations on separate lines after the
178 diagnostic message, rather than as a prefix to the message. */
179 bool m_show_nesting;
180
181 /* Set to false to suppress location-printing when showing nested
182 diagnostics, for use in DejaGnu tests. */
183 bool m_show_locations_in_nesting;
184
185 /* If true, then add "(level N):" when printing nested diagnostics. */
186 bool m_show_nesting_levels;
187};
188
189} // namespace diagnostics
190
191#endif /* ! GCC_DIAGNOSTICS_TEXT_SINK_H */
192

source code of gcc/diagnostics/text-sink.h