1 //===--- raw_ostream.h - Raw output stream ----------------------*- C++ -*-===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 // 9 // This file defines the raw_ostream class. 10 // 11 //===----------------------------------------------------------------------===// 12 13 #ifndef LLVM_SUPPORT_RAW_OSTREAM_H 14 #define LLVM_SUPPORT_RAW_OSTREAM_H 15 16 #include "llvm/ADT/SmallVector.h" 17 #include "llvm/ADT/StringRef.h" 18 #include "llvm/Support/DataTypes.h" 19 #include <cassert> 20 #include <cstddef> 21 #include <cstdint> 22 #include <cstring> 23 #include <optional> 24 #include <string> 25 #include <string_view> 26 #include <system_error> 27 #include <type_traits> 28 29 namespace llvm { 30 31 class Duration; 32 class formatv_object_base; 33 class format_object_base; 34 class FormattedString; 35 class FormattedNumber; 36 class FormattedBytes; 37 template <class T> class [[nodiscard]] Expected; 38 39 namespace sys { 40 namespace fs { 41 enum FileAccess : unsigned; 42 enum OpenFlags : unsigned; 43 enum CreationDisposition : unsigned; 44 class FileLocker; 45 } // end namespace fs 46 } // end namespace sys 47 48 /// This class implements an extremely fast bulk output stream that can *only* 49 /// output to a stream. It does not support seeking, reopening, rewinding, line 50 /// buffered disciplines etc. It is a simple buffer that outputs 51 /// a chunk at a time. 52 class raw_ostream { 53 public: 54 // Class kinds to support LLVM-style RTTI. 55 enum class OStreamKind { 56 OK_OStream, 57 OK_FDStream, 58 }; 59 60 private: 61 OStreamKind Kind; 62 63 /// The buffer is handled in such a way that the buffer is 64 /// uninitialized, unbuffered, or out of space when OutBufCur >= 65 /// OutBufEnd. Thus a single comparison suffices to determine if we 66 /// need to take the slow path to write a single character. 67 /// 68 /// The buffer is in one of three states: 69 /// 1. Unbuffered (BufferMode == Unbuffered) 70 /// 1. Uninitialized (BufferMode != Unbuffered && OutBufStart == 0). 71 /// 2. Buffered (BufferMode != Unbuffered && OutBufStart != 0 && 72 /// OutBufEnd - OutBufStart >= 1). 73 /// 74 /// If buffered, then the raw_ostream owns the buffer if (BufferMode == 75 /// InternalBuffer); otherwise the buffer has been set via SetBuffer and is 76 /// managed by the subclass. 77 /// 78 /// If a subclass installs an external buffer using SetBuffer then it can wait 79 /// for a \see write_impl() call to handle the data which has been put into 80 /// this buffer. 81 char *OutBufStart, *OutBufEnd, *OutBufCur; 82 bool ColorEnabled = false; 83 84 /// Optional stream this stream is tied to. If this stream is written to, the 85 /// tied-to stream will be flushed first. 86 raw_ostream *TiedStream = nullptr; 87 88 enum class BufferKind { 89 Unbuffered = 0, 90 InternalBuffer, 91 ExternalBuffer 92 } BufferMode; 93 94 public: 95 // color order matches ANSI escape sequence, don't change 96 enum class Colors { 97 BLACK = 0, 98 RED, 99 GREEN, 100 YELLOW, 101 BLUE, 102 MAGENTA, 103 CYAN, 104 WHITE, 105 SAVEDCOLOR, 106 RESET, 107 }; 108 109 static constexpr Colors BLACK = Colors::BLACK; 110 static constexpr Colors RED = Colors::RED; 111 static constexpr Colors GREEN = Colors::GREEN; 112 static constexpr Colors YELLOW = Colors::YELLOW; 113 static constexpr Colors BLUE = Colors::BLUE; 114 static constexpr Colors MAGENTA = Colors::MAGENTA; 115 static constexpr Colors CYAN = Colors::CYAN; 116 static constexpr Colors WHITE = Colors::WHITE; 117 static constexpr Colors SAVEDCOLOR = Colors::SAVEDCOLOR; 118 static constexpr Colors RESET = Colors::RESET; 119 120 explicit raw_ostream(bool unbuffered = false, 121 OStreamKind K = OStreamKind::OK_OStream) 122 : Kind(K), BufferMode(unbuffered ? BufferKind::Unbuffered 123 : BufferKind::InternalBuffer) { 124 // Start out ready to flush. 125 OutBufStart = OutBufEnd = OutBufCur = nullptr; 126 } 127 128 raw_ostream(const raw_ostream &) = delete; 129 void operator=(const raw_ostream &) = delete; 130 131 virtual ~raw_ostream(); 132 133 /// tell - Return the current offset with the file. 134 uint64_t tell() const { return current_pos() + GetNumBytesInBuffer(); } 135 136 OStreamKind get_kind() const { return Kind; } 137 138 //===--------------------------------------------------------------------===// 139 // Configuration Interface 140 //===--------------------------------------------------------------------===// 141 142 /// If possible, pre-allocate \p ExtraSize bytes for stream data. 143 /// i.e. it extends internal buffers to keep additional ExtraSize bytes. 144 /// So that the stream could keep at least tell() + ExtraSize bytes 145 /// without re-allocations. reserveExtraSpace() does not change 146 /// the size/data of the stream. 147 virtual void reserveExtraSpace(uint64_t ExtraSize) {} 148 149 /// Set the stream to be buffered, with an automatically determined buffer 150 /// size. 151 void SetBuffered(); 152 153 /// Set the stream to be buffered, using the specified buffer size. 154 void SetBufferSize(size_t Size) { 155 flush(); 156 SetBufferAndMode(new char[Size], Size, BufferKind::InternalBuffer); 157 } 158 159 size_t GetBufferSize() const { 160 // If we're supposed to be buffered but haven't actually gotten around 161 // to allocating the buffer yet, return the value that would be used. 162 if (BufferMode != BufferKind::Unbuffered && OutBufStart == nullptr) 163 return preferred_buffer_size(); 164 165 // Otherwise just return the size of the allocated buffer. 166 return OutBufEnd - OutBufStart; 167 } 168 169 /// Set the stream to be unbuffered. When unbuffered, the stream will flush 170 /// after every write. This routine will also flush the buffer immediately 171 /// when the stream is being set to unbuffered. 172 void SetUnbuffered() { 173 flush(); 174 SetBufferAndMode(nullptr, 0, BufferKind::Unbuffered); 175 } 176 177 size_t GetNumBytesInBuffer() const { 178 return OutBufCur - OutBufStart; 179 } 180 181 //===--------------------------------------------------------------------===// 182 // Data Output Interface 183 //===--------------------------------------------------------------------===// 184 185 void flush() { 186 if (OutBufCur != OutBufStart) 187 flush_nonempty(); 188 } 189 190 raw_ostream &operator<<(char C) { 191 if (OutBufCur >= OutBufEnd) 192 return write(C); 193 *OutBufCur++ = C; 194 return *this; 195 } 196 197 raw_ostream &operator<<(unsigned char C) { 198 if (OutBufCur >= OutBufEnd) 199 return write(C); 200 *OutBufCur++ = C; 201 return *this; 202 } 203 204 raw_ostream &operator<<(signed char C) { 205 if (OutBufCur >= OutBufEnd) 206 return write(C); 207 *OutBufCur++ = C; 208 return *this; 209 } 210 211 raw_ostream &operator<<(StringRef Str) { 212 // Inline fast path, particularly for strings with a known length. 213 size_t Size = Str.size(); 214 215 // Make sure we can use the fast path. 216 if (Size > (size_t)(OutBufEnd - OutBufCur)) 217 return write(Str.data(), Size); 218 219 if (Size) { 220 memcpy(OutBufCur, Str.data(), Size); 221 OutBufCur += Size; 222 } 223 return *this; 224 } 225 226 #if defined(__cpp_char8_t) 227 // When using `char8_t *` integers or pointers are written to the ostream 228 // instead of UTF-8 code as one might expect. This might lead to unexpected 229 // behavior, especially as `u8""` literals are of type `char8_t*` instead of 230 // type `char_t*` from C++20 onwards. Thus we disallow using them with 231 // raw_ostreams. 232 // If you have u8"" literals to stream, you can rewrite them as ordinary 233 // literals with escape sequences 234 // e.g. replace `u8"\u00a0"` by `"\xc2\xa0"` 235 // or use `reinterpret_cast`: 236 // e.g. replace `u8"\u00a0"` by `reinterpret_cast<const char *>(u8"\u00a0")` 237 raw_ostream &operator<<(const char8_t *Str) = delete; 238 #endif 239 240 raw_ostream &operator<<(const char *Str) { 241 // Inline fast path, particularly for constant strings where a sufficiently 242 // smart compiler will simplify strlen. 243 244 return this->operator<<(StringRef(Str)); 245 } 246 247 raw_ostream &operator<<(const std::string &Str) { 248 // Avoid the fast path, it would only increase code size for a marginal win. 249 return write(Str.data(), Str.length()); 250 } 251 252 raw_ostream &operator<<(const std::string_view &Str) { 253 return write(Str.data(), Str.length()); 254 } 255 256 raw_ostream &operator<<(const SmallVectorImpl<char> &Str) { 257 return write(Str.data(), Str.size()); 258 } 259 260 raw_ostream &operator<<(unsigned long N); 261 raw_ostream &operator<<(long N); 262 raw_ostream &operator<<(unsigned long long N); 263 raw_ostream &operator<<(long long N); 264 raw_ostream &operator<<(const void *P); 265 266 raw_ostream &operator<<(unsigned int N) { 267 return this->operator<<(static_cast<unsigned long>(N)); 268 } 269 270 raw_ostream &operator<<(int N) { 271 return this->operator<<(static_cast<long>(N)); 272 } 273 274 raw_ostream &operator<<(double N); 275 276 /// Output \p N in hexadecimal, without any prefix or padding. 277 raw_ostream &write_hex(unsigned long long N); 278 279 // Change the foreground color of text. 280 raw_ostream &operator<<(Colors C); 281 282 /// Output a formatted UUID with dash separators. 283 using uuid_t = uint8_t[16]; 284 raw_ostream &write_uuid(const uuid_t UUID); 285 286 /// Output \p Str, turning '\\', '\t', '\n', '"', and anything that doesn't 287 /// satisfy llvm::isPrint into an escape sequence. 288 raw_ostream &write_escaped(StringRef Str, bool UseHexEscapes = false); 289 290 raw_ostream &write(unsigned char C); 291 raw_ostream &write(const char *Ptr, size_t Size); 292 293 // Formatted output, see the format() function in Support/Format.h. 294 raw_ostream &operator<<(const format_object_base &Fmt); 295 296 // Formatted output, see the leftJustify() function in Support/Format.h. 297 raw_ostream &operator<<(const FormattedString &); 298 299 // Formatted output, see the formatHex() function in Support/Format.h. 300 raw_ostream &operator<<(const FormattedNumber &); 301 302 // Formatted output, see the formatv() function in Support/FormatVariadic.h. 303 raw_ostream &operator<<(const formatv_object_base &); 304 305 // Formatted output, see the format_bytes() function in Support/Format.h. 306 raw_ostream &operator<<(const FormattedBytes &); 307 308 /// indent - Insert 'NumSpaces' spaces. 309 raw_ostream &indent(unsigned NumSpaces); 310 311 /// write_zeros - Insert 'NumZeros' nulls. 312 raw_ostream &write_zeros(unsigned NumZeros); 313 314 /// Changes the foreground color of text that will be output from this point 315 /// forward. 316 /// @param Color ANSI color to use, the special SAVEDCOLOR can be used to 317 /// change only the bold attribute, and keep colors untouched 318 /// @param Bold bold/brighter text, default false 319 /// @param BG if true change the background, default: change foreground 320 /// @returns itself so it can be used within << invocations 321 virtual raw_ostream &changeColor(enum Colors Color, bool Bold = false, 322 bool BG = false); 323 324 /// Resets the colors to terminal defaults. Call this when you are done 325 /// outputting colored text, or before program exit. 326 virtual raw_ostream &resetColor(); 327 328 /// Reverses the foreground and background colors. 329 virtual raw_ostream &reverseColor(); 330 331 /// This function determines if this stream is connected to a "tty" or 332 /// "console" window. That is, the output would be displayed to the user 333 /// rather than being put on a pipe or stored in a file. 334 virtual bool is_displayed() const { return false; } 335 336 /// This function determines if this stream is displayed and supports colors. 337 /// The result is unaffected by calls to enable_color(). 338 virtual bool has_colors() const { return is_displayed(); } 339 340 // Enable or disable colors. Once enable_colors(false) is called, 341 // changeColor() has no effect until enable_colors(true) is called. 342 virtual void enable_colors(bool enable) { ColorEnabled = enable; } 343 344 bool colors_enabled() const { return ColorEnabled; } 345 346 /// Tie this stream to the specified stream. Replaces any existing tied-to 347 /// stream. Specifying a nullptr unties the stream. 348 void tie(raw_ostream *TieTo) { TiedStream = TieTo; } 349 350 //===--------------------------------------------------------------------===// 351 // Subclass Interface 352 //===--------------------------------------------------------------------===// 353 354 private: 355 /// The is the piece of the class that is implemented by subclasses. This 356 /// writes the \p Size bytes starting at 357 /// \p Ptr to the underlying stream. 358 /// 359 /// This function is guaranteed to only be called at a point at which it is 360 /// safe for the subclass to install a new buffer via SetBuffer. 361 /// 362 /// \param Ptr The start of the data to be written. For buffered streams this 363 /// is guaranteed to be the start of the buffer. 364 /// 365 /// \param Size The number of bytes to be written. 366 /// 367 /// \invariant { Size > 0 } 368 virtual void write_impl(const char *Ptr, size_t Size) = 0; 369 370 /// Return the current position within the stream, not counting the bytes 371 /// currently in the buffer. 372 virtual uint64_t current_pos() const = 0; 373 374 protected: 375 /// Use the provided buffer as the raw_ostream buffer. This is intended for 376 /// use only by subclasses which can arrange for the output to go directly 377 /// into the desired output buffer, instead of being copied on each flush. 378 void SetBuffer(char *BufferStart, size_t Size) { 379 SetBufferAndMode(BufferStart, Size, BufferKind::ExternalBuffer); 380 } 381 382 /// Return an efficient buffer size for the underlying output mechanism. 383 virtual size_t preferred_buffer_size() const; 384 385 /// Return the beginning of the current stream buffer, or 0 if the stream is 386 /// unbuffered. 387 const char *getBufferStart() const { return OutBufStart; } 388 389 //===--------------------------------------------------------------------===// 390 // Private Interface 391 //===--------------------------------------------------------------------===// 392 private: 393 /// Install the given buffer and mode. 394 void SetBufferAndMode(char *BufferStart, size_t Size, BufferKind Mode); 395 396 /// Flush the current buffer, which is known to be non-empty. This outputs the 397 /// currently buffered data and resets the buffer to empty. 398 void flush_nonempty(); 399 400 /// Copy data into the buffer. Size must not be greater than the number of 401 /// unused bytes in the buffer. 402 void copy_to_buffer(const char *Ptr, size_t Size); 403 404 /// Compute whether colors should be used and do the necessary work such as 405 /// flushing. The result is affected by calls to enable_color(). 406 bool prepare_colors(); 407 408 /// Flush the tied-to stream (if present) and then write the required data. 409 void flush_tied_then_write(const char *Ptr, size_t Size); 410 411 virtual void anchor(); 412 }; 413 414 /// Call the appropriate insertion operator, given an rvalue reference to a 415 /// raw_ostream object and return a stream of the same type as the argument. 416 template <typename OStream, typename T> 417 std::enable_if_t<!std::is_reference<OStream>::value && 418 std::is_base_of<raw_ostream, OStream>::value, 419 OStream &&> 420 operator<<(OStream &&OS, const T &Value) { 421 OS << Value; 422 return std::move(OS); 423 } 424 425 /// An abstract base class for streams implementations that also support a 426 /// pwrite operation. This is useful for code that can mostly stream out data, 427 /// but needs to patch in a header that needs to know the output size. 428 class raw_pwrite_stream : public raw_ostream { 429 virtual void pwrite_impl(const char *Ptr, size_t Size, uint64_t Offset) = 0; 430 void anchor() override; 431 432 public: 433 explicit raw_pwrite_stream(bool Unbuffered = false, 434 OStreamKind K = OStreamKind::OK_OStream) 435 : raw_ostream(Unbuffered, K) {} 436 void pwrite(const char *Ptr, size_t Size, uint64_t Offset) { 437 #ifndef NDEBUG 438 uint64_t Pos = tell(); 439 // /dev/null always reports a pos of 0, so we cannot perform this check 440 // in that case. 441 if (Pos) 442 assert(Size + Offset <= Pos && "We don't support extending the stream"); 443 #endif 444 pwrite_impl(Ptr, Size, Offset); 445 } 446 }; 447 448 //===----------------------------------------------------------------------===// 449 // File Output Streams 450 //===----------------------------------------------------------------------===// 451 452 /// A raw_ostream that writes to a file descriptor. 453 /// 454 class raw_fd_ostream : public raw_pwrite_stream { 455 int FD; 456 bool ShouldClose; 457 bool SupportsSeeking = false; 458 bool IsRegularFile = false; 459 mutable std::optional<bool> HasColors; 460 461 #ifdef _WIN32 462 /// True if this fd refers to a Windows console device. Mintty and other 463 /// terminal emulators are TTYs, but they are not consoles. 464 bool IsWindowsConsole = false; 465 #endif 466 467 std::error_code EC; 468 469 uint64_t pos = 0; 470 471 /// See raw_ostream::write_impl. 472 void write_impl(const char *Ptr, size_t Size) override; 473 474 void pwrite_impl(const char *Ptr, size_t Size, uint64_t Offset) override; 475 476 /// Return the current position within the stream, not counting the bytes 477 /// currently in the buffer. 478 uint64_t current_pos() const override { return pos; } 479 480 /// Determine an efficient buffer size. 481 size_t preferred_buffer_size() const override; 482 483 void anchor() override; 484 485 protected: 486 /// Set the flag indicating that an output error has been encountered. 487 void error_detected(std::error_code EC) { this->EC = EC; } 488 489 /// Return the file descriptor. 490 int get_fd() const { return FD; } 491 492 // Update the file position by increasing \p Delta. 493 void inc_pos(uint64_t Delta) { pos += Delta; } 494 495 public: 496 /// Open the specified file for writing. If an error occurs, information 497 /// about the error is put into EC, and the stream should be immediately 498 /// destroyed; 499 /// \p Flags allows optional flags to control how the file will be opened. 500 /// 501 /// As a special case, if Filename is "-", then the stream will use 502 /// STDOUT_FILENO instead of opening a file. This will not close the stdout 503 /// descriptor. 504 raw_fd_ostream(StringRef Filename, std::error_code &EC); 505 raw_fd_ostream(StringRef Filename, std::error_code &EC, 506 sys::fs::CreationDisposition Disp); 507 raw_fd_ostream(StringRef Filename, std::error_code &EC, 508 sys::fs::FileAccess Access); 509 raw_fd_ostream(StringRef Filename, std::error_code &EC, 510 sys::fs::OpenFlags Flags); 511 raw_fd_ostream(StringRef Filename, std::error_code &EC, 512 sys::fs::CreationDisposition Disp, sys::fs::FileAccess Access, 513 sys::fs::OpenFlags Flags); 514 515 /// FD is the file descriptor that this writes to. If ShouldClose is true, 516 /// this closes the file when the stream is destroyed. If FD is for stdout or 517 /// stderr, it will not be closed. 518 raw_fd_ostream(int fd, bool shouldClose, bool unbuffered = false, 519 OStreamKind K = OStreamKind::OK_OStream); 520 521 ~raw_fd_ostream() override; 522 523 /// Manually flush the stream and close the file. Note that this does not call 524 /// fsync. 525 void close(); 526 527 bool supportsSeeking() const { return SupportsSeeking; } 528 529 bool isRegularFile() const { return IsRegularFile; } 530 531 /// Flushes the stream and repositions the underlying file descriptor position 532 /// to the offset specified from the beginning of the file. 533 uint64_t seek(uint64_t off); 534 535 bool is_displayed() const override; 536 537 bool has_colors() const override; 538 539 std::error_code error() const { return EC; } 540 541 /// Return the value of the flag in this raw_fd_ostream indicating whether an 542 /// output error has been encountered. 543 /// This doesn't implicitly flush any pending output. Also, it doesn't 544 /// guarantee to detect all errors unless the stream has been closed. 545 bool has_error() const { return bool(EC); } 546 547 /// Set the flag read by has_error() to false. If the error flag is set at the 548 /// time when this raw_ostream's destructor is called, report_fatal_error is 549 /// called to report the error. Use clear_error() after handling the error to 550 /// avoid this behavior. 551 /// 552 /// "Errors should never pass silently. 553 /// Unless explicitly silenced." 554 /// - from The Zen of Python, by Tim Peters 555 /// 556 void clear_error() { EC = std::error_code(); } 557 558 /// Locks the underlying file. 559 /// 560 /// @returns RAII object that releases the lock upon leaving the scope, if the 561 /// locking was successful. Otherwise returns corresponding 562 /// error code. 563 /// 564 /// The function blocks the current thread until the lock become available or 565 /// error occurs. 566 /// 567 /// Possible use of this function may be as follows: 568 /// 569 /// @code{.cpp} 570 /// if (auto L = stream.lock()) { 571 /// // ... do action that require file to be locked. 572 /// } else { 573 /// handleAllErrors(std::move(L.takeError()), [&](ErrorInfoBase &EIB) { 574 /// // ... handle lock error. 575 /// }); 576 /// } 577 /// @endcode 578 [[nodiscard]] Expected<sys::fs::FileLocker> lock(); 579 580 /// Tries to lock the underlying file within the specified period. 581 /// 582 /// @returns RAII object that releases the lock upon leaving the scope, if the 583 /// locking was successful. Otherwise returns corresponding 584 /// error code. 585 /// 586 /// It is used as @ref lock. 587 [[nodiscard]] Expected<sys::fs::FileLocker> 588 tryLockFor(Duration const &Timeout); 589 }; 590 591 /// This returns a reference to a raw_fd_ostream for standard output. Use it 592 /// like: outs() << "foo" << "bar"; 593 raw_fd_ostream &outs(); 594 595 /// This returns a reference to a raw_ostream for standard error. 596 /// Use it like: errs() << "foo" << "bar"; 597 /// By default, the stream is tied to stdout to ensure stdout is flushed before 598 /// stderr is written, to ensure the error messages are written in their 599 /// expected place. 600 raw_fd_ostream &errs(); 601 602 /// This returns a reference to a raw_ostream which simply discards output. 603 raw_ostream &nulls(); 604 605 //===----------------------------------------------------------------------===// 606 // File Streams 607 //===----------------------------------------------------------------------===// 608 609 /// A raw_ostream of a file for reading/writing/seeking. 610 /// 611 class raw_fd_stream : public raw_fd_ostream { 612 public: 613 /// Open the specified file for reading/writing/seeking. If an error occurs, 614 /// information about the error is put into EC, and the stream should be 615 /// immediately destroyed. 616 raw_fd_stream(StringRef Filename, std::error_code &EC); 617 618 /// This reads the \p Size bytes into a buffer pointed by \p Ptr. 619 /// 620 /// \param Ptr The start of the buffer to hold data to be read. 621 /// 622 /// \param Size The number of bytes to be read. 623 /// 624 /// On success, the number of bytes read is returned, and the file position is 625 /// advanced by this number. On error, -1 is returned, use error() to get the 626 /// error code. 627 ssize_t read(char *Ptr, size_t Size); 628 629 /// Check if \p OS is a pointer of type raw_fd_stream*. 630 static bool classof(const raw_ostream *OS); 631 }; 632 633 //===----------------------------------------------------------------------===// 634 // Output Stream Adaptors 635 //===----------------------------------------------------------------------===// 636 637 /// A raw_ostream that writes to an std::string. This is a simple adaptor 638 /// class. This class does not encounter output errors. 639 /// raw_string_ostream operates without a buffer, delegating all memory 640 /// management to the std::string. Thus the std::string is always up-to-date, 641 /// may be used directly and there is no need to call flush(). 642 class raw_string_ostream : public raw_ostream { 643 std::string &OS; 644 645 /// See raw_ostream::write_impl. 646 void write_impl(const char *Ptr, size_t Size) override; 647 648 /// Return the current position within the stream, not counting the bytes 649 /// currently in the buffer. 650 uint64_t current_pos() const override { return OS.size(); } 651 652 public: 653 explicit raw_string_ostream(std::string &O) : OS(O) { 654 SetUnbuffered(); 655 } 656 657 /// Returns the string's reference. In most cases it is better to simply use 658 /// the underlying std::string directly. 659 /// TODO: Consider removing this API. 660 std::string &str() { return OS; } 661 662 void reserveExtraSpace(uint64_t ExtraSize) override { 663 OS.reserve(tell() + ExtraSize); 664 } 665 }; 666 667 /// A raw_ostream that writes to an SmallVector or SmallString. This is a 668 /// simple adaptor class. This class does not encounter output errors. 669 /// raw_svector_ostream operates without a buffer, delegating all memory 670 /// management to the SmallString. Thus the SmallString is always up-to-date, 671 /// may be used directly and there is no need to call flush(). 672 class raw_svector_ostream : public raw_pwrite_stream { 673 SmallVectorImpl<char> &OS; 674 675 /// See raw_ostream::write_impl. 676 void write_impl(const char *Ptr, size_t Size) override; 677 678 void pwrite_impl(const char *Ptr, size_t Size, uint64_t Offset) override; 679 680 /// Return the current position within the stream. 681 uint64_t current_pos() const override; 682 683 public: 684 /// Construct a new raw_svector_ostream. 685 /// 686 /// \param O The vector to write to; this should generally have at least 128 687 /// bytes free to avoid any extraneous memory overhead. 688 explicit raw_svector_ostream(SmallVectorImpl<char> &O) : OS(O) { 689 SetUnbuffered(); 690 } 691 692 ~raw_svector_ostream() override = default; 693 694 void flush() = delete; 695 696 /// Return a StringRef for the vector contents. 697 StringRef str() const { return StringRef(OS.data(), OS.size()); } 698 699 void reserveExtraSpace(uint64_t ExtraSize) override { 700 OS.reserve(tell() + ExtraSize); 701 } 702 }; 703 704 /// A raw_ostream that discards all output. 705 class raw_null_ostream : public raw_pwrite_stream { 706 /// See raw_ostream::write_impl. 707 void write_impl(const char *Ptr, size_t size) override; 708 void pwrite_impl(const char *Ptr, size_t Size, uint64_t Offset) override; 709 710 /// Return the current position within the stream, not counting the bytes 711 /// currently in the buffer. 712 uint64_t current_pos() const override; 713 714 public: 715 explicit raw_null_ostream() = default; 716 ~raw_null_ostream() override; 717 }; 718 719 class buffer_ostream : public raw_svector_ostream { 720 raw_ostream &OS; 721 SmallVector<char, 0> Buffer; 722 723 void anchor() override; 724 725 public: 726 buffer_ostream(raw_ostream &OS) : raw_svector_ostream(Buffer), OS(OS) {} 727 ~buffer_ostream() override { OS << str(); } 728 }; 729 730 class buffer_unique_ostream : public raw_svector_ostream { 731 std::unique_ptr<raw_ostream> OS; 732 SmallVector<char, 0> Buffer; 733 734 void anchor() override; 735 736 public: 737 buffer_unique_ostream(std::unique_ptr<raw_ostream> OS) 738 : raw_svector_ostream(Buffer), OS(std::move(OS)) { 739 // Turn off buffering on OS, which we now own, to avoid allocating a buffer 740 // when the destructor writes only to be immediately flushed again. 741 this->OS->SetUnbuffered(); 742 } 743 ~buffer_unique_ostream() override { *OS << str(); } 744 }; 745 746 class Error; 747 748 /// This helper creates an output stream and then passes it to \p Write. 749 /// The stream created is based on the specified \p OutputFileName: 750 /// llvm::outs for "-", raw_null_ostream for "/dev/null", and raw_fd_ostream 751 /// for other names. For raw_fd_ostream instances, the stream writes to 752 /// a temporary file. The final output file is atomically replaced with the 753 /// temporary file after the \p Write function is finished. 754 Error writeToOutput(StringRef OutputFileName, 755 std::function<Error(raw_ostream &)> Write); 756 757 raw_ostream &operator<<(raw_ostream &OS, std::nullopt_t); 758 759 template <typename T, typename = decltype(std::declval<raw_ostream &>() 760 << std::declval<const T &>())> 761 raw_ostream &operator<<(raw_ostream &OS, const std::optional<T> &O) { 762 if (O) 763 OS << *O; 764 else 765 OS << std::nullopt; 766 return OS; 767 } 768 769 } // end namespace llvm 770 771 #endif // LLVM_SUPPORT_RAW_OSTREAM_H 772