1 /*
2 * Copyright (c) 1997, 2025, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation.
8 *
9 * This code is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
12 * version 2 for more details (a copy is included in the LICENSE file that
13 * accompanied this code).
14 *
15 * You should have received a copy of the GNU General Public License version
16 * 2 along with this work; if not, write to the Free Software Foundation,
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
18 *
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
20 * or visit www.oracle.com if you need additional information or have any
21 * questions.
22 *
23 */
24
25 #ifndef SHARE_UTILITIES_OSTREAM_HPP
26 #define SHARE_UTILITIES_OSTREAM_HPP
27
28 #include "memory/allocation.hpp"
29 #include "runtime/timer.hpp"
30 #include "utilities/globalDefinitions.hpp"
31 #include "utilities/macros.hpp"
32
33 DEBUG_ONLY(class ResourceMark;)
34
35 // Output streams for printing
36 //
37 // Printing guidelines:
38 // Where possible, please use tty->print() and tty->print_cr().
39 // For product mode VM warnings use warning() which internally uses tty.
40 // In places where tty is not initialized yet or too much overhead,
41 // we may use jio_printf:
42 // jio_fprintf(defaultStream::output_stream(), "Message");
43 // This allows for redirection via -XX:+DisplayVMOutputToStdout and
44 // -XX:+DisplayVMOutputToStderr.
45
46 class outputStream : public CHeapObjBase {
47 friend class StreamIndentor;
48
49 private:
50 NONCOPYABLE(outputStream);
51 int _indentation; // current indentation
52 bool _autoindent; // if true, every line starts with indentation
53
54 protected:
55 int _position; // visual position on the current line
56 uint64_t _precount; // number of chars output, less than _position
57 TimeStamp _stamp; // for time stamps
58 char* _scratch; // internal scratch buffer for printf
59 size_t _scratch_len; // size of internal scratch buffer
60
61 // Returns whether a newline was seen or not
62 bool update_position(const char* s, size_t len);
63
64 // Processes the given format string and the supplied arguments
65 // to produce a formatted string in the supplied buffer. Returns
66 // the formatted string (in the buffer). If the formatted string
67 // would be longer than the buffer, it is truncated.
68 //
69 // If the format string is a plain string (no format specifiers)
70 // or is exactly "%s" to print a supplied argument string, then
71 // the buffer is ignored, and we return the string directly.
72 // However, if `add_cr` is true then we have to copy the string
73 // into the buffer, which risks truncation if the string is too long.
74 //
75 // The `result_len` reference is always set to the length of the returned string.
76 //
77 // If add_cr is true then the cr will always be placed in the buffer (buffer minimum size is 2).
78 //
79 // In a debug build, if truncation occurs a VM warning is issued.
80 static const char* do_vsnprintf(char* buffer, size_t buflen,
81 const char* format, va_list ap,
82 bool add_cr,
83 size_t& result_len) ATTRIBUTE_PRINTF(3, 0);
84
85 // calls do_vsnprintf and writes output to stream; uses an on-stack buffer.
86 void do_vsnprintf_and_write_with_automatic_buffer(const char* format, va_list ap, bool add_cr) ATTRIBUTE_PRINTF(2, 0);
87 // calls do_vsnprintf and writes output to stream; uses the user-provided buffer;
88 void do_vsnprintf_and_write_with_scratch_buffer(const char* format, va_list ap, bool add_cr) ATTRIBUTE_PRINTF(2, 0);
89 // calls do_vsnprintf, then writes output to stream.
90 void do_vsnprintf_and_write(const char* format, va_list ap, bool add_cr) ATTRIBUTE_PRINTF(2, 0);
91
92 // Automatic indentation. Returns old autoindent state.
93 bool set_autoindent(bool value);
94
95 public:
96 class TestSupport; // Unit test support
97
98 // creation
99 outputStream(bool has_time_stamps = false);
100
101 // indentation
102 outputStream& indent();
103 void inc() { _indentation++; };
104 void dec() { _indentation--; };
105 void inc(int n) { _indentation += n; };
106 void dec(int n) { _indentation -= n; };
107 int indentation() const { return _indentation; }
108 void set_indentation(int i) { _indentation = i; }
109 int fill_to(int col);
110 void move_to(int col, int slop = 6, int min_space = 2);
111
112 // sizing
113 int position() const { return _position; }
114 julong count() const { return _precount + _position; }
115 void set_count(julong count) { _precount = count - _position; }
116 void set_position(int pos) { _position = pos; }
117
118 // printing
119 // Note that (v)print_cr forces the use of internal buffering to allow
120 // appending of the "cr". This can lead to truncation if the buffer is
121 // too small.
122
123 void print(const char* format, ...) ATTRIBUTE_PRINTF(2, 3);
124 void print_cr(const char* format, ...) ATTRIBUTE_PRINTF(2, 3);
125 void vprint(const char *format, va_list argptr) ATTRIBUTE_PRINTF(2, 0);
126 void vprint_cr(const char* format, va_list argptr) ATTRIBUTE_PRINTF(2, 0);
127 void print_raw(const char* str) { print_raw(str, strlen(str)); }
128 void print_raw(const char* str, size_t len);
129 void print_raw_cr(const char* str) { print_raw(str); cr(); }
130 void print_raw_cr(const char* str, size_t len) { print_raw(str, len); cr(); }
131 void print_data(void* data, size_t len, bool with_ascii, bool rel_addr=true);
132 void put(char ch);
133 void sp(int count = 1);
134 void cr();
135 void bol() { if (_position > 0) cr(); }
136
137
138 // Time stamp
139 TimeStamp& time_stamp() { return _stamp; }
140 void stamp();
141 void stamp(bool guard, const char* prefix, const char* suffix);
142 void stamp(bool guard) {
143 stamp(guard, "", ": ");
144 }
145 // Date stamp
146 void date_stamp(bool guard, const char* prefix, const char* suffix);
147 // A simplified call that includes a suffix of ": "
148 void date_stamp(bool guard) {
149 date_stamp(guard, "", ": ");
150 }
151
152 // portable printing of 64 bit integers
153 void print_jlong(jlong value);
154 void print_julong(julong value);
155
156 // flushing
157 virtual void flush() {}
158 virtual void write(const char* str, size_t len) = 0;
159 virtual void rotate_log(bool force, outputStream* out = nullptr) {} // GC log rotation
160 virtual ~outputStream() {} // close properly on deletion
161
162 // Caller may specify their own scratch buffer to use for printing; otherwise,
163 // an automatic buffer on the stack (with O_BUFLEN len) is used.
164 void set_scratch_buffer(char* p, size_t len) { _scratch = p; _scratch_len = len; }
165
166 void dec_cr() { dec(); cr(); }
167 void inc_cr() { inc(); cr(); }
168 };
169
170 // standard output
171 // ANSI C++ name collision
172 extern outputStream* tty; // tty output
173
174 // outputStream indentation. When used, indentation is automatically applied
175 // when printing on the stream using the following APIs:
176 // print(), print_cr(), print_raw(), print_raw_cr()
177 class StreamIndentor {
178 private:
179 outputStream* const _stream;
180 const int _indentation;
181 const bool _old_autoindent;
182 NONCOPYABLE(StreamIndentor);
183
184 public:
185 StreamIndentor(outputStream* os, int indentation = 2) :
186 _stream(os),
187 _indentation(indentation),
188 _old_autoindent(_stream->set_autoindent(true)) {
189
190 _stream->inc(_indentation);
191 }
192
193 ~StreamIndentor() {
194 _stream->dec(_indentation);
195 _stream->set_autoindent(_old_autoindent);
196 }
197 };
198
199 // advisory locking for the shared tty stream:
200 class ttyLocker: StackObj {
201 friend class ttyUnlocker;
202 private:
203 intx _holder;
204
205 public:
206 static intx hold_tty(); // returns a "holder" token
207 static void release_tty(intx holder); // must witness same token
208 static bool release_tty_if_locked(); // returns true if lock was released
209 static void break_tty_lock_for_safepoint(intx holder);
210
211 ttyLocker() { _holder = hold_tty(); }
212 ~ttyLocker() { release_tty(_holder); }
213 };
214
215 // Release the tty lock if it's held and reacquire it if it was
216 // locked. Used to avoid lock ordering problems.
217 class ttyUnlocker: StackObj {
218 private:
219 bool _was_locked;
220 public:
221 ttyUnlocker() {
222 _was_locked = ttyLocker::release_tty_if_locked();
223 }
224 ~ttyUnlocker() {
225 if (_was_locked) {
226 ttyLocker::hold_tty();
227 }
228 }
229 };
230
231 // for writing to strings; buffer will expand automatically.
232 // Buffer will always be zero-terminated.
233 class stringStream : public outputStream {
234 DEBUG_ONLY(bool _is_frozen = false);
235 char* _buffer;
236 size_t _written; // Number of characters written, excluding termin. zero
237 size_t _capacity;
238 const bool _is_fixed;
239 char _small_buffer[48];
240
241 // Grow backing buffer to desired capacity.
242 void grow(size_t new_capacity);
243
244 // zero terminate at buffer_pos.
245 void zero_terminate();
246
247 public:
248 // Create a stringStream using an internal buffer of initially initial_bufsize size;
249 // will be enlarged on demand. There is no maximum cap.
250 stringStream(size_t initial_capacity = 0);
251 // Creates a stringStream using a caller-provided buffer. Will truncate silently if
252 // it overflows.
253 stringStream(char* fixed_buffer, size_t fixed_buffer_size);
254 ~stringStream();
255 virtual void write(const char* c, size_t len);
256 // Return number of characters written into buffer, excluding terminating zero and
257 // subject to truncation in static buffer mode.
258 size_t size() const { return _written; }
259 // Returns internal buffer containing the accumulated string.
260 // Returned buffer is only guaranteed to be valid as long as stream is not modified
261 const char* base() const { return _buffer; }
262 // Freezes stringStream (no further modifications possible) and returns pointer to it.
263 // No-op if stream is frozen already.
264 // Returns the internal buffer containing the accumulated string.
265 const char* freeze() NOT_DEBUG(const) {
266 DEBUG_ONLY(_is_frozen = true);
267 return _buffer;
268 };
269 void reset();
270 bool is_empty() const { return _buffer[0] == '\0'; }
271 // Copy to a resource, or C-heap, array as requested
272 char* as_string(bool c_heap = false) const;
273 char* as_string(Arena* arena) const;
274 };
275
276 class fileStream : public outputStream {
277 protected:
278 FILE* _file;
279 bool _need_close;
280 public:
281 fileStream() { _file = nullptr; _need_close = false; }
282 fileStream(const char* file_name);
283 fileStream(const char* file_name, const char* opentype);
284 fileStream(FILE* file, bool need_close = false) { _file = file; _need_close = need_close; }
285 ~fileStream();
286 bool is_open() const { return _file != nullptr; }
287 virtual void write(const char* c, size_t len);
288 // unlike other classes in this file, fileStream can perform input as well as output
289 size_t read(void* data, size_t size) {
290 if (_file == nullptr) return 0;
291 return ::fread(data, 1, size, _file);
292 }
293 size_t read(void *data, size_t size, size_t count) {
294 return read(data, size * count);
295 }
296 void close() {
297 if (_file == nullptr || !_need_close) return;
298 fclose(_file);
299 _need_close = false;
300 }
301 long fileSize();
302 void flush();
303 };
304
305 // unlike fileStream, fdStream does unbuffered I/O by calling
306 // open() and write() directly. It is async-safe, but output
307 // from multiple thread may be mixed together. Used by fatal
308 // error handler.
309 class fdStream : public outputStream {
310 protected:
311 int _fd;
312 static fdStream _stdout_stream;
313 static fdStream _stderr_stream;
314 public:
315 fdStream(int fd = -1) : _fd(fd) { }
316 bool is_open() const { return _fd != -1; }
317 void set_fd(int fd) { _fd = fd; }
318 int fd() const { return _fd; }
319 virtual void write(const char* c, size_t len);
320 void flush() {};
321
322 // predefined streams for unbuffered IO to stdout, stderr
323 static fdStream* stdout_stream() { return &_stdout_stream; }
324 static fdStream* stderr_stream() { return &_stderr_stream; }
325 };
326
327 // A /dev/null equivalent stream
328 class nullStream : public outputStream {
329 public:
330 void write(const char* c, size_t len) {}
331 void flush() {};
332 };
333
334 void ostream_init();
335 void ostream_init_log();
336 void ostream_exit();
337 void ostream_abort();
338 const char* make_log_name(const char* log_name, const char* force_directory);
339
340 // In the non-fixed buffer case an underlying buffer will be created and
341 // managed in C heap. Not MT-safe.
342 class bufferedStream : public outputStream {
343 protected:
344 char* buffer;
345 size_t buffer_pos;
346 size_t buffer_max;
347 size_t buffer_length;
348 bool truncated;
349 public:
350 bufferedStream(size_t initial_bufsize = 256, size_t bufmax = 1024*1024*10);
351 ~bufferedStream();
352 virtual void write(const char* c, size_t len);
353 size_t size() { return buffer_pos; }
354 const char* base() { return buffer; }
355 void reset() { buffer_pos = 0; _precount = 0; _position = 0; }
356 char* as_string();
357 };
358
359 #define O_BUFLEN 2000 // max size of output of individual print() methods
360
361 #ifndef PRODUCT
362
363 class networkStream : public bufferedStream {
364
365 private:
366 int _socket;
367
368 public:
369 networkStream();
370 ~networkStream();
371
372 bool connect(const char *host, short port);
373 bool is_open() const { return _socket != -1; }
374 ssize_t read(char *buf, size_t len);
375 void close();
376 virtual void flush();
377 };
378
379 #endif
380
381 #endif // SHARE_UTILITIES_OSTREAM_HPP