LLVM 22.0.0git
raw_ostream.cpp
Go to the documentation of this file.
1//===--- raw_ostream.cpp - Implement the raw_ostream classes --------------===//
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 implements support for bulk buffered stream output.
10//
11//===----------------------------------------------------------------------===//
12
15#include "llvm/Config/config.h"
21#include "llvm/Support/Format.h"
27#include <algorithm>
28#include <cerrno>
29#include <cstdio>
30#include <sys/stat.h>
31
32// <fcntl.h> may provide O_BINARY.
33# include <fcntl.h>
34
35#if defined(HAVE_UNISTD_H)
36# include <unistd.h>
37#endif
38
39#if defined(__CYGWIN__)
40#include <io.h>
41#endif
42
43#if defined(_MSC_VER)
44#include <io.h>
45#ifndef STDIN_FILENO
46# define STDIN_FILENO 0
47#endif
48#ifndef STDOUT_FILENO
49# define STDOUT_FILENO 1
50#endif
51#ifndef STDERR_FILENO
52# define STDERR_FILENO 2
53#endif
54#endif
55
56#ifdef _WIN32
60#endif
61
62using namespace llvm;
63
65 // raw_ostream's subclasses should take care to flush the buffer
66 // in their destructors.
67 assert(OutBufCur == OutBufStart &&
68 "raw_ostream destructor called with non-empty buffer!");
69
70 if (BufferMode == BufferKind::InternalBuffer)
71 delete [] OutBufStart;
72}
73
75#ifdef _WIN32
76 // On Windows BUFSIZ is only 512 which results in more calls to write. This
77 // overhead can cause significant performance degradation. Therefore use a
78 // better default.
79 return (16 * 1024);
80#else
81 // BUFSIZ is intended to be a reasonable default.
82 return BUFSIZ;
83#endif
84}
85
87 // Ask the subclass to determine an appropriate buffer size.
88 if (size_t Size = preferred_buffer_size())
90 else
91 // It may return 0, meaning this stream should be unbuffered.
93}
94
95void raw_ostream::SetBufferAndMode(char *BufferStart, size_t Size,
96 BufferKind Mode) {
97 assert(((Mode == BufferKind::Unbuffered && !BufferStart && Size == 0) ||
98 (Mode != BufferKind::Unbuffered && BufferStart && Size != 0)) &&
99 "stream must be unbuffered or have at least one byte");
100 // Make sure the current buffer is free of content (we can't flush here; the
101 // child buffer management logic will be in write_impl).
102 assert(GetNumBytesInBuffer() == 0 && "Current buffer is non-empty!");
103
104 if (BufferMode == BufferKind::InternalBuffer)
105 delete [] OutBufStart;
106 OutBufStart = BufferStart;
107 OutBufEnd = OutBufStart+Size;
108 OutBufCur = OutBufStart;
109 BufferMode = Mode;
110
111 assert(OutBufStart <= OutBufEnd && "Invalid size!");
112}
113
115 write_integer(*this, static_cast<uint64_t>(N), 0, IntegerStyle::Integer);
116 return *this;
117}
118
120 write_integer(*this, static_cast<int64_t>(N), 0, IntegerStyle::Integer);
121 return *this;
122}
123
125 write_integer(*this, static_cast<uint64_t>(N), 0, IntegerStyle::Integer);
126 return *this;
127}
128
130 write_integer(*this, static_cast<int64_t>(N), 0, IntegerStyle::Integer);
131 return *this;
132}
133
136 return *this;
137}
138
140 if (C == Colors::RESET)
141 resetColor();
142 else
143 changeColor(C);
144 return *this;
145}
146
148 for (int Idx = 0; Idx < 16; ++Idx) {
149 *this << format("%02" PRIX32, UUID[Idx]);
150 if (Idx == 3 || Idx == 5 || Idx == 7 || Idx == 9)
151 *this << "-";
152 }
153 return *this;
154}
155
156
158 bool UseHexEscapes) {
159 for (unsigned char c : Str) {
160 switch (c) {
161 case '\\':
162 *this << '\\' << '\\';
163 break;
164 case '\t':
165 *this << '\\' << 't';
166 break;
167 case '\n':
168 *this << '\\' << 'n';
169 break;
170 case '"':
171 *this << '\\' << '"';
172 break;
173 default:
174 if (isPrint(c)) {
175 *this << c;
176 break;
177 }
178
179 // Write out the escaped representation.
180 if (UseHexEscapes) {
181 *this << '\\' << 'x';
182 *this << hexdigit((c >> 4) & 0xF);
183 *this << hexdigit((c >> 0) & 0xF);
184 } else {
185 // Always use a full 3-character octal escape.
186 *this << '\\';
187 *this << char('0' + ((c >> 6) & 7));
188 *this << char('0' + ((c >> 3) & 7));
189 *this << char('0' + ((c >> 0) & 7));
190 }
191 }
192 }
193
194 return *this;
195}
196
198 llvm::write_hex(*this, (uintptr_t)P, HexPrintStyle::PrefixLower);
199 return *this;
200}
201
204 return *this;
205}
206
207void raw_ostream::flush_nonempty() {
208 assert(OutBufCur > OutBufStart && "Invalid call to flush_nonempty.");
209 size_t Length = OutBufCur - OutBufStart;
210 OutBufCur = OutBufStart;
211 write_impl(OutBufStart, Length);
212}
213
215 // Group exceptional cases into a single branch.
216 if (LLVM_UNLIKELY(OutBufCur >= OutBufEnd)) {
217 if (LLVM_UNLIKELY(!OutBufStart)) {
218 if (BufferMode == BufferKind::Unbuffered) {
219 write_impl(reinterpret_cast<char *>(&C), 1);
220 return *this;
221 }
222 // Set up a buffer and start over.
223 SetBuffered();
224 return write(C);
225 }
226
227 flush_nonempty();
228 }
229
230 *OutBufCur++ = C;
231 return *this;
232}
233
234raw_ostream &raw_ostream::write(const char *Ptr, size_t Size) {
235 // Group exceptional cases into a single branch.
236 if (LLVM_UNLIKELY(size_t(OutBufEnd - OutBufCur) < Size)) {
237 if (LLVM_UNLIKELY(!OutBufStart)) {
238 if (BufferMode == BufferKind::Unbuffered) {
239 write_impl(Ptr, Size);
240 return *this;
241 }
242 // Set up a buffer and start over.
243 SetBuffered();
244 return write(Ptr, Size);
245 }
246
247 size_t NumBytes = OutBufEnd - OutBufCur;
248
249 // If the buffer is empty at this point we have a string that is larger
250 // than the buffer. Directly write the chunk that is a multiple of the
251 // preferred buffer size and put the remainder in the buffer.
252 if (LLVM_UNLIKELY(OutBufCur == OutBufStart)) {
253 assert(NumBytes != 0 && "undefined behavior");
254 size_t BytesToWrite = Size - (Size % NumBytes);
255 write_impl(Ptr, BytesToWrite);
256 size_t BytesRemaining = Size - BytesToWrite;
257 if (BytesRemaining > size_t(OutBufEnd - OutBufCur)) {
258 // Too much left over to copy into our buffer.
259 return write(Ptr + BytesToWrite, BytesRemaining);
260 }
261 copy_to_buffer(Ptr + BytesToWrite, BytesRemaining);
262 return *this;
263 }
264
265 // We don't have enough space in the buffer to fit the string in. Insert as
266 // much as possible, flush and start over with the remainder.
267 copy_to_buffer(Ptr, NumBytes);
268 flush_nonempty();
269 return write(Ptr + NumBytes, Size - NumBytes);
270 }
271
272 copy_to_buffer(Ptr, Size);
273
274 return *this;
275}
276
277void raw_ostream::copy_to_buffer(const char *Ptr, size_t Size) {
278 assert(Size <= size_t(OutBufEnd - OutBufCur) && "Buffer overrun!");
279
280 // Handle short strings specially, memcpy isn't very good at very short
281 // strings.
282 switch (Size) {
283 case 4: OutBufCur[3] = Ptr[3]; [[fallthrough]];
284 case 3: OutBufCur[2] = Ptr[2]; [[fallthrough]];
285 case 2: OutBufCur[1] = Ptr[1]; [[fallthrough]];
286 case 1: OutBufCur[0] = Ptr[0]; [[fallthrough]];
287 case 0: break;
288 default:
289 memcpy(OutBufCur, Ptr, Size);
290 break;
291 }
292
293 OutBufCur += Size;
294}
295
296// Formatted output.
298 // If we have more than a few bytes left in our output buffer, try
299 // formatting directly onto its end.
300 size_t NextBufferSize = 127;
301 size_t BufferBytesLeft = OutBufEnd - OutBufCur;
302 if (BufferBytesLeft > 3) {
303 size_t BytesUsed = Fmt.print(OutBufCur, BufferBytesLeft);
304
305 // Common case is that we have plenty of space.
306 if (BytesUsed <= BufferBytesLeft) {
307 OutBufCur += BytesUsed;
308 return *this;
309 }
310
311 // Otherwise, we overflowed and the return value tells us the size to try
312 // again with.
313 NextBufferSize = BytesUsed;
314 }
315
316 // If we got here, we didn't have enough space in the output buffer for the
317 // string. Try printing into a SmallVector that is resized to have enough
318 // space. Iterate until we win.
320
321 while (true) {
322 V.resize(NextBufferSize);
323
324 // Try formatting into the SmallVector.
325 size_t BytesUsed = Fmt.print(V.data(), NextBufferSize);
326
327 // If BytesUsed fit into the vector, we win.
328 if (BytesUsed <= NextBufferSize)
329 return write(V.data(), BytesUsed);
330
331 // Otherwise, try again with a new size.
332 assert(BytesUsed > NextBufferSize && "Didn't grow buffer!?");
333 NextBufferSize = BytesUsed;
334 }
335}
336
338 Obj.format(*this);
339 return *this;
340}
341
343 unsigned LeftIndent = 0;
344 unsigned RightIndent = 0;
345 const ssize_t Difference = FS.Width - FS.Str.size();
346 if (Difference > 0) {
347 switch (FS.Justify) {
349 break;
351 RightIndent = Difference;
352 break;
354 LeftIndent = Difference;
355 break;
357 LeftIndent = Difference / 2;
358 RightIndent = Difference - LeftIndent;
359 break;
360 }
361 }
362 indent(LeftIndent);
363 (*this) << FS.Str;
364 indent(RightIndent);
365 return *this;
366}
367
369 if (FN.Hex) {
370 HexPrintStyle Style;
371 if (FN.Upper && FN.HexPrefix)
373 else if (FN.Upper && !FN.HexPrefix)
374 Style = HexPrintStyle::Upper;
375 else if (!FN.Upper && FN.HexPrefix)
377 else
378 Style = HexPrintStyle::Lower;
379 llvm::write_hex(*this, FN.HexValue, Style, FN.Width);
380 } else {
382 llvm::raw_svector_ostream Stream(Buffer);
383 llvm::write_integer(Stream, FN.DecValue, 0, IntegerStyle::Integer);
384 if (Buffer.size() < FN.Width)
385 indent(FN.Width - Buffer.size());
386 (*this) << Buffer;
387 }
388 return *this;
389}
390
392 if (FB.Bytes.empty())
393 return *this;
394
395 size_t LineIndex = 0;
396 auto Bytes = FB.Bytes;
397 const size_t Size = Bytes.size();
399 uint64_t OffsetWidth = 0;
400 if (FB.FirstByteOffset) {
401 // Figure out how many nibbles are needed to print the largest offset
402 // represented by this data set, so that we can align the offset field
403 // to the right width.
404 size_t Lines = Size / FB.NumPerLine;
405 uint64_t MaxOffset = *FB.FirstByteOffset + Lines * FB.NumPerLine;
406 unsigned Power = 0;
407 if (MaxOffset > 0)
408 Power = llvm::Log2_64_Ceil(MaxOffset);
409 OffsetWidth = std::max<uint64_t>(4, llvm::alignTo(Power, 4) / 4);
410 }
411
412 // The width of a block of data including all spaces for group separators.
413 unsigned NumByteGroups =
414 alignTo(FB.NumPerLine, FB.ByteGroupSize) / FB.ByteGroupSize;
415 unsigned BlockCharWidth = FB.NumPerLine * 2 + NumByteGroups - 1;
416
417 while (!Bytes.empty()) {
418 indent(FB.IndentLevel);
419
420 if (FB.FirstByteOffset) {
421 uint64_t Offset = *FB.FirstByteOffset;
422 llvm::write_hex(*this, Offset + LineIndex, HPS, OffsetWidth);
423 *this << ": ";
424 }
425
426 auto Line = Bytes.take_front(FB.NumPerLine);
427
428 size_t CharsPrinted = 0;
429 // Print the hex bytes for this line in groups
430 for (size_t I = 0; I < Line.size(); ++I, CharsPrinted += 2) {
431 if (I && (I % FB.ByteGroupSize) == 0) {
432 ++CharsPrinted;
433 *this << " ";
434 }
435 llvm::write_hex(*this, Line[I], HPS, 2);
436 }
437
438 if (FB.ASCII) {
439 // Print any spaces needed for any bytes that we didn't print on this
440 // line so that the ASCII bytes are correctly aligned.
441 assert(BlockCharWidth >= CharsPrinted);
442 indent(BlockCharWidth - CharsPrinted + 2);
443 *this << "|";
444
445 // Print the ASCII char values for each byte on this line
446 for (uint8_t Byte : Line) {
447 if (isPrint(Byte))
448 *this << static_cast<char>(Byte);
449 else
450 *this << '.';
451 }
452 *this << '|';
453 }
454
455 Bytes = Bytes.drop_front(Line.size());
456 LineIndex += Line.size();
457 if (LineIndex < Size)
458 *this << '\n';
459 }
460 return *this;
461}
462
463template <char C>
464static raw_ostream &write_padding(raw_ostream &OS, unsigned NumChars) {
465 static const char Chars[] = {C, C, C, C, C, C, C, C, C, C, C, C, C, C, C, C,
466 C, C, C, C, C, C, C, C, C, C, C, C, C, C, C, C,
467 C, C, C, C, C, C, C, C, C, C, C, C, C, C, C, C,
468 C, C, C, C, C, C, C, C, C, C, C, C, C, C, C, C,
469 C, C, C, C, C, C, C, C, C, C, C, C, C, C, C, C};
470
471 // Usually the indentation is small, handle it with a fastpath.
472 if (NumChars < std::size(Chars))
473 return OS.write(Chars, NumChars);
474
475 while (NumChars) {
476 unsigned NumToWrite = std::min(NumChars, (unsigned)std::size(Chars) - 1);
477 OS.write(Chars, NumToWrite);
478 NumChars -= NumToWrite;
479 }
480 return OS;
481}
482
483/// indent - Insert 'NumSpaces' spaces.
484raw_ostream &raw_ostream::indent(unsigned NumSpaces) {
485 return write_padding<' '>(*this, NumSpaces);
486}
487
488/// write_zeros - Insert 'NumZeros' nulls.
490 return write_padding<'\0'>(*this, NumZeros);
491}
492
493bool raw_ostream::prepare_colors() {
494 // Colors were explicitly disabled.
495 if (!ColorEnabled)
496 return false;
497
498 // Colors require changing the terminal but this stream is not going to a
499 // terminal.
501 return false;
502
504 flush();
505
506 return true;
507}
508
509raw_ostream &raw_ostream::changeColor(enum Colors colors, bool bold, bool bg) {
510 if (!prepare_colors())
511 return *this;
512
513 const char *colorcode =
514 (colors == SAVEDCOLOR)
516 : sys::Process::OutputColor(static_cast<char>(colors), bold, bg);
517 if (colorcode)
518 write(colorcode, strlen(colorcode));
519 return *this;
520}
521
523 if (!prepare_colors())
524 return *this;
525
526 if (const char *colorcode = sys::Process::ResetColor())
527 write(colorcode, strlen(colorcode));
528 return *this;
529}
530
532 if (!prepare_colors())
533 return *this;
534
535 if (const char *colorcode = sys::Process::OutputReverse())
536 write(colorcode, strlen(colorcode));
537 return *this;
538}
539
540void raw_ostream::anchor() {}
541
542//===----------------------------------------------------------------------===//
543// Formatted Output
544//===----------------------------------------------------------------------===//
545
546// Out of line virtual method.
549
550//===----------------------------------------------------------------------===//
551// raw_fd_ostream
552//===----------------------------------------------------------------------===//
553
554static int getFD(StringRef Filename, std::error_code &EC,
556 sys::fs::OpenFlags Flags) {
558 "Cannot make a raw_ostream from a read-only descriptor!");
559
560 // Handle "-" as stdout. Note that when we do this, we consider ourself
561 // the owner of stdout and may set the "binary" flag globally based on Flags.
562 if (Filename == "-") {
563 EC = std::error_code();
564 // Change stdout's text/binary mode based on the Flags.
566 return STDOUT_FILENO;
567 }
568
569 int FD;
571 EC = sys::fs::openFileForReadWrite(Filename, FD, Disp, Flags);
572 else
573 EC = sys::fs::openFileForWrite(Filename, FD, Disp, Flags);
574 if (EC)
575 return -1;
576
577 return FD;
578}
579
580raw_fd_ostream::raw_fd_ostream(StringRef Filename, std::error_code &EC)
581 : raw_fd_ostream(Filename, EC, sys::fs::CD_CreateAlways, sys::fs::FA_Write,
582 sys::fs::OF_None) {}
583
584raw_fd_ostream::raw_fd_ostream(StringRef Filename, std::error_code &EC,
586 : raw_fd_ostream(Filename, EC, Disp, sys::fs::FA_Write, sys::fs::OF_None) {}
587
588raw_fd_ostream::raw_fd_ostream(StringRef Filename, std::error_code &EC,
590 : raw_fd_ostream(Filename, EC, sys::fs::CD_CreateAlways, Access,
591 sys::fs::OF_None) {}
592
593raw_fd_ostream::raw_fd_ostream(StringRef Filename, std::error_code &EC,
594 sys::fs::OpenFlags Flags)
595 : raw_fd_ostream(Filename, EC, sys::fs::CD_CreateAlways, sys::fs::FA_Write,
596 Flags) {}
597
598raw_fd_ostream::raw_fd_ostream(StringRef Filename, std::error_code &EC,
601 sys::fs::OpenFlags Flags)
602 : raw_fd_ostream(getFD(Filename, EC, Disp, Access, Flags), true) {}
603
604/// FD is the file descriptor that this writes to. If ShouldClose is true, this
605/// closes the file when the stream is destroyed.
606raw_fd_ostream::raw_fd_ostream(int fd, bool shouldClose, bool unbuffered,
607 OStreamKind K)
608 : raw_pwrite_stream(unbuffered, K), FD(fd), ShouldClose(shouldClose) {
609 if (FD < 0 ) {
610 ShouldClose = false;
611 return;
612 }
613
614 enable_colors(true);
615
616 // Do not attempt to close stdout or stderr. We used to try to maintain the
617 // property that tools that support writing file to stdout should not also
618 // write informational output to stdout, but in practice we were never able to
619 // maintain this invariant. Many features have been added to LLVM and clang
620 // (-fdump-record-layouts, optimization remarks, etc) that print to stdout, so
621 // users must simply be aware that mixed output and remarks is a possibility.
622 if (FD <= STDERR_FILENO)
623 ShouldClose = false;
624
625#ifdef _WIN32
626 // Check if this is a console device. This is not equivalent to isatty.
627 IsWindowsConsole =
628 ::GetFileType((HANDLE)::_get_osfhandle(fd)) == FILE_TYPE_CHAR;
629#endif
630
631 // Get the starting position.
632 off_t loc = ::lseek(FD, 0, SEEK_CUR);
634 std::error_code EC = status(FD, Status);
635 IsRegularFile = Status.type() == sys::fs::file_type::regular_file;
636#ifdef _WIN32
637 // MSVCRT's _lseek(SEEK_CUR) doesn't return -1 for pipes.
638 SupportsSeeking = !EC && IsRegularFile;
639#else
640 SupportsSeeking = !EC && loc != (off_t)-1;
641#endif
642 if (!SupportsSeeking)
643 pos = 0;
644 else
645 pos = static_cast<uint64_t>(loc);
646}
647
649 if (FD >= 0) {
650 flush();
651 if (ShouldClose) {
653 error_detected(EC);
654 }
655 }
656
657#ifdef __MINGW32__
658 // On mingw, global dtors should not call exit().
659 // report_fatal_error() invokes exit(). We know report_fatal_error()
660 // might not write messages to stderr when any errors were detected
661 // on FD == 2.
662 if (FD == 2) return;
663#endif
664
665 // If there are any pending errors, report them now. Clients wishing
666 // to avoid report_fatal_error calls should check for errors with
667 // has_error() and clear the error flag with clear_error() before
668 // destructing raw_ostream objects which may have errors.
669 if (has_error())
670 reportFatalUsageError(Twine("IO failure on output stream: ") +
671 error().message());
672}
673
674#if defined(_WIN32)
675// The most reliable way to print unicode in a Windows console is with
676// WriteConsoleW. To use that, first transcode from UTF-8 to UTF-16. This
677// assumes that LLVM programs always print valid UTF-8 to the console. The data
678// might not be UTF-8 for two major reasons:
679// 1. The program is printing binary (-filetype=obj -o -), in which case it
680// would have been gibberish anyway.
681// 2. The program is printing text in a semi-ascii compatible codepage like
682// shift-jis or cp1252.
683//
684// Most LLVM programs don't produce non-ascii text unless they are quoting
685// user source input. A well-behaved LLVM program should either validate that
686// the input is UTF-8 or transcode from the local codepage to UTF-8 before
687// quoting it. If they don't, this may mess up the encoding, but this is still
688// probably the best compromise we can make.
689static bool write_console_impl(int FD, StringRef Data) {
691
692 // Fall back to ::write if it wasn't valid UTF-8.
693 if (auto EC = sys::windows::UTF8ToUTF16(Data, WideText))
694 return false;
695
696 // On Windows 7 and earlier, WriteConsoleW has a low maximum amount of data
697 // that can be written to the console at a time.
698 size_t MaxWriteSize = WideText.size();
700 MaxWriteSize = 32767;
701
702 size_t WCharsWritten = 0;
703 do {
704 size_t WCharsToWrite =
705 std::min(MaxWriteSize, WideText.size() - WCharsWritten);
706 DWORD ActuallyWritten;
707 bool Success =
708 ::WriteConsoleW((HANDLE)::_get_osfhandle(FD), &WideText[WCharsWritten],
709 WCharsToWrite, &ActuallyWritten,
710 /*Reserved=*/nullptr);
711
712 // The most likely reason for WriteConsoleW to fail is that FD no longer
713 // points to a console. Fall back to ::write. If this isn't the first loop
714 // iteration, something is truly wrong.
715 if (!Success)
716 return false;
717
718 WCharsWritten += ActuallyWritten;
719 } while (WCharsWritten != WideText.size());
720 return true;
721}
722#endif
723
724void raw_fd_ostream::write_impl(const char *Ptr, size_t Size) {
725 if (TiedStream)
726 TiedStream->flush();
727
728 assert(FD >= 0 && "File already closed.");
729 pos += Size;
730
731#if defined(_WIN32)
732 // If this is a Windows console device, try re-encoding from UTF-8 to UTF-16
733 // and using WriteConsoleW. If that fails, fall back to plain write().
734 if (IsWindowsConsole)
735 if (write_console_impl(FD, StringRef(Ptr, Size)))
736 return;
737#endif
738
739 // The maximum write size is limited to INT32_MAX. A write
740 // greater than SSIZE_MAX is implementation-defined in POSIX,
741 // and Windows _write requires 32 bit input.
742 size_t MaxWriteSize = INT32_MAX;
743
744#if defined(__linux__)
745 // It is observed that Linux returns EINVAL for a very large write (>2G).
746 // Make it a reasonably small value.
747 MaxWriteSize = 1024 * 1024 * 1024;
748#endif
749
750 do {
751 size_t ChunkSize = std::min(Size, MaxWriteSize);
752 ssize_t ret = ::write(FD, Ptr, ChunkSize);
753
754 if (ret < 0) {
755 // If it's a recoverable error, swallow it and retry the write.
756 //
757 // Ideally we wouldn't ever see EAGAIN or EWOULDBLOCK here, since
758 // raw_ostream isn't designed to do non-blocking I/O. However, some
759 // programs, such as old versions of bjam, have mistakenly used
760 // O_NONBLOCK. For compatibility, emulate blocking semantics by
761 // spinning until the write succeeds. If you don't want spinning,
762 // don't use O_NONBLOCK file descriptors with raw_ostream.
763 if (errno == EINTR || errno == EAGAIN
764#ifdef EWOULDBLOCK
765 || errno == EWOULDBLOCK
766#endif
767 )
768 continue;
769
770#ifdef _WIN32
771 // Windows equivalents of SIGPIPE/EPIPE.
772 DWORD WinLastError = GetLastError();
773 if (WinLastError == ERROR_BROKEN_PIPE ||
774 (WinLastError == ERROR_NO_DATA && errno == EINVAL)) {
775 llvm::sys::CallOneShotPipeSignalHandler();
776 errno = EPIPE;
777 }
778#endif
779 // Otherwise it's a non-recoverable error. Note it and quit.
781 break;
782 }
783
784 // The write may have written some or all of the data. Update the
785 // size and buffer pointer to reflect the remainder that needs
786 // to be written. If there are no bytes left, we're done.
787 Ptr += ret;
788 Size -= ret;
789 } while (Size > 0);
790}
791
793 assert(ShouldClose);
794 ShouldClose = false;
795 flush();
797 error_detected(EC);
798 FD = -1;
799}
800
802 assert(SupportsSeeking && "Stream does not support seeking!");
803 flush();
804#ifdef _WIN32
805 pos = ::_lseeki64(FD, off, SEEK_SET);
806#else
807 pos = ::lseek(FD, off, SEEK_SET);
808#endif
809 if (pos == (uint64_t)-1)
811 return pos;
812}
813
814void raw_fd_ostream::pwrite_impl(const char *Ptr, size_t Size,
816 uint64_t Pos = tell();
817 seek(Offset);
818 write(Ptr, Size);
819 seek(Pos);
820}
821
823#if defined(_WIN32)
824 // Disable buffering for console devices. Console output is re-encoded from
825 // UTF-8 to UTF-16 on Windows, and buffering it would require us to split the
826 // buffer on a valid UTF-8 codepoint boundary. Terminal buffering is disabled
827 // below on most other OSs, so do the same thing on Windows and avoid that
828 // complexity.
829 if (IsWindowsConsole)
830 return 0;
832#elif defined(__MVS__)
833 // The buffer size on z/OS is defined with macro BUFSIZ, which can be
834 // retrieved by invoking function raw_ostream::preferred_buffer_size().
836#else
837 assert(FD >= 0 && "File not yet open!");
838 struct stat statbuf;
839 if (fstat(FD, &statbuf) != 0)
840 return 0;
841
842 // If this is a terminal, don't use buffering. Line buffering
843 // would be a more traditional thing to do, but it's not worth
844 // the complexity.
845 if (S_ISCHR(statbuf.st_mode) && is_displayed())
846 return 0;
847 // Return the preferred block size.
848 return statbuf.st_blksize;
849#endif
850}
851
855
857 if (!HasColors)
859 return *HasColors;
860}
861
863 std::error_code EC = sys::fs::lockFile(FD);
864 if (!EC)
865 return sys::fs::FileLocker(FD);
866 return errorCodeToError(EC);
867}
868
871 std::error_code EC = sys::fs::tryLockFile(FD, Timeout.getDuration());
872 if (!EC)
873 return sys::fs::FileLocker(FD);
874 return errorCodeToError(EC);
875}
876
877void raw_fd_ostream::anchor() {}
878
879//===----------------------------------------------------------------------===//
880// outs(), errs(), nulls()
881//===----------------------------------------------------------------------===//
882
884 // Set buffer settings to model stdout behavior.
885 std::error_code EC;
886
887 // On z/OS we need to enable auto conversion
888 static std::error_code EC1 = enableAutoConversion(STDOUT_FILENO);
889 assert(!EC1);
890 (void)EC1;
891
892 static raw_fd_ostream S("-", EC, sys::fs::OF_None);
893 assert(!EC);
894 return S;
895}
896
898 // On z/OS we need to enable auto conversion
899 static std::error_code EC = enableAutoConversion(STDERR_FILENO);
900 assert(!EC);
901 (void)EC;
902
903 // Set standard error to be unbuffered.
904 static raw_fd_ostream S(STDERR_FILENO, false, true);
905 return S;
906}
907
908/// nulls() - This returns a reference to a raw_ostream which discards output.
910 static raw_null_ostream S;
911 return S;
912}
913
914//===----------------------------------------------------------------------===//
915// File Streams
916//===----------------------------------------------------------------------===//
917
918raw_fd_stream::raw_fd_stream(StringRef Filename, std::error_code &EC)
919 : raw_fd_ostream(getFD(Filename, EC, sys::fs::CD_CreateAlways,
920 sys::fs::FA_Write | sys::fs::FA_Read,
921 sys::fs::OF_None),
923 if (EC)
924 return;
925
926 if (!isRegularFile())
927 EC = std::make_error_code(std::errc::invalid_argument);
928}
929
930raw_fd_stream::raw_fd_stream(int fd, bool shouldClose)
931 : raw_fd_ostream(fd, shouldClose, false, OStreamKind::OK_FDStream) {}
932
933ssize_t raw_fd_stream::read(char *Ptr, size_t Size) {
934 assert(get_fd() >= 0 && "File already closed.");
935 ssize_t Ret = ::read(get_fd(), (void *)Ptr, Size);
936 if (Ret >= 0)
937 inc_pos(Ret);
938 else
940 return Ret;
941}
942
944 return OS->get_kind() == OStreamKind::OK_FDStream;
945}
946
947//===----------------------------------------------------------------------===//
948// raw_string_ostream
949//===----------------------------------------------------------------------===//
950
951void raw_string_ostream::write_impl(const char *Ptr, size_t Size) {
952 OS.append(Ptr, Size);
953}
954
955//===----------------------------------------------------------------------===//
956// raw_svector_ostream
957//===----------------------------------------------------------------------===//
958
959uint64_t raw_svector_ostream::current_pos() const { return OS.size(); }
960
961void raw_svector_ostream::write_impl(const char *Ptr, size_t Size) {
962 OS.append(Ptr, Ptr + Size);
963}
964
965void raw_svector_ostream::pwrite_impl(const char *Ptr, size_t Size,
966 uint64_t Offset) {
967 memcpy(OS.data() + Offset, Ptr, Size);
968}
969
971 return OS->get_kind() == OStreamKind::OK_SVecStream;
972}
973
974//===----------------------------------------------------------------------===//
975// raw_null_ostream
976//===----------------------------------------------------------------------===//
977
979#ifndef NDEBUG
980 // ~raw_ostream asserts that the buffer is empty. This isn't necessary
981 // with raw_null_ostream, but it's better to have raw_null_ostream follow
982 // the rules than to change the rules just for raw_null_ostream.
983 flush();
984#endif
985}
986
987void raw_null_ostream::write_impl(const char *Ptr, size_t Size) {
988}
989
990uint64_t raw_null_ostream::current_pos() const {
991 return 0;
992}
993
994void raw_null_ostream::pwrite_impl(const char *Ptr, size_t Size,
995 uint64_t Offset) {}
996
997void raw_pwrite_stream::anchor() {}
998
999void buffer_ostream::anchor() {}
1000
1001void buffer_unique_ostream::anchor() {}
1002
1004 std::function<Error(raw_ostream &)> Write) {
1005 if (OutputFileName == "-")
1006 return Write(outs());
1007
1008 if (OutputFileName == "/dev/null") {
1009 raw_null_ostream Out;
1010 return Write(Out);
1011 }
1012
1013 unsigned Mode = sys::fs::all_read | sys::fs::all_write;
1015 sys::fs::TempFile::create(OutputFileName + ".temp-stream-%%%%%%", Mode);
1016 if (!Temp)
1017 return createFileError(OutputFileName, Temp.takeError());
1018
1019 raw_fd_ostream Out(Temp->FD, false);
1020
1021 if (Error E = Write(Out)) {
1022 if (Error DiscardError = Temp->discard())
1023 return joinErrors(std::move(E), std::move(DiscardError));
1024 return E;
1025 }
1026 Out.flush();
1027
1028 return Temp->keep(OutputFileName);
1029}
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
#define LLVM_UNLIKELY(EXPR)
Definition Compiler.h:336
DXIL Resource Access
#define STDOUT_FILENO
Definition InitLLVM.cpp:28
#define STDERR_FILENO
Definition InitLLVM.cpp:31
#define I(x, y, z)
Definition MD5.cpp:58
#define P(N)
Provides a library for accessing information about this process and other processes on the operating ...
This file contains some functions that are useful when dealing with strings.
std::pair< llvm::MachO::Target, std::string > UUID
bool empty() const
empty - Check if the array is empty.
Definition ArrayRef.h:138
Lightweight error class with error context and mandatory checking.
Definition Error.h:159
Tagged union holding either a T or a Error.
Definition Error.h:485
Error takeError()
Take ownership of the stored error.
Definition Error.h:612
This is a helper class used for format_hex() and format_decimal().
Definition Format.h:169
This is a helper class for left_justify, right_justify, and center_justify.
Definition Format.h:134
SmallString - A SmallString is just a SmallVector with methods and accessors that make it work better...
Definition SmallString.h:26
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
StringRef - Represent a constant reference to a string, i.e.
Definition StringRef.h:55
Twine - A lightweight data structure for efficiently representing the concatenation of temporary valu...
Definition Twine.h:82
This is a helper class used for handling formatted output.
Definition Format.h:40
unsigned print(char *Buffer, unsigned BufferSize) const
Format the object into the specified buffer.
Definition Format.h:56
void format(raw_ostream &S) const
A raw_ostream that writes to a file descriptor.
bool is_displayed() const override
This function determines if this stream is connected to a "tty" or "console" window.
bool has_error() const
Return the value of the flag in this raw_fd_ostream indicating whether an output error has been encou...
std::error_code error() const
void close()
Manually flush the stream and close the file.
void inc_pos(uint64_t Delta)
Expected< sys::fs::FileLocker > lock()
Locks the underlying file.
bool has_colors() const override
This function determines if this stream is displayed and supports colors.
bool isRegularFile() const
uint64_t seek(uint64_t off)
Flushes the stream and repositions the underlying file descriptor position to the offset specified fr...
int get_fd() const
Return the file descriptor.
Expected< sys::fs::FileLocker > tryLockFor(Duration const &Timeout)
Tries to lock the underlying file within the specified period.
raw_fd_ostream(StringRef Filename, std::error_code &EC)
Open the specified file for writing.
void error_detected(std::error_code EC)
Set the flag indicating that an output error has been encountered.
static LLVM_ABI bool classof(const raw_ostream *OS)
Check if OS is a pointer of type raw_fd_stream*.
LLVM_ABI raw_fd_stream(StringRef Filename, std::error_code &EC)
Open the specified file for reading/writing/seeking.
LLVM_ABI ssize_t read(char *Ptr, size_t Size)
This reads the Size bytes into a buffer pointed by Ptr.
A raw_ostream that discards all output.
This class implements an extremely fast bulk output stream that can only output to a stream.
Definition raw_ostream.h:53
raw_ostream & write_zeros(unsigned NumZeros)
write_zeros - Insert 'NumZeros' nulls.
raw_ostream(bool unbuffered=false, OStreamKind K=OStreamKind::OK_OStream)
uint64_t tell() const
tell - Return the current offset with the file.
void SetBufferSize(size_t Size)
Set the stream to be buffered, using the specified buffer size.
virtual raw_ostream & changeColor(enum Colors Color, bool Bold=false, bool BG=false)
Changes the foreground color of text that will be output from this point forward.
raw_ostream & write_hex(unsigned long long N)
Output N in hexadecimal, without any prefix or padding.
virtual raw_ostream & resetColor()
Resets the colors to terminal defaults.
raw_ostream & write_uuid(const uuid_t UUID)
raw_ostream & operator<<(char C)
virtual ~raw_ostream()
raw_ostream & write_escaped(StringRef Str, bool UseHexEscapes=false)
Output Str, turning '\', '\t', ' ', '"', and anything that doesn't satisfy llvm::isPrint into an esca...
virtual raw_ostream & reverseColor()
Reverses the foreground and background colors.
virtual size_t preferred_buffer_size() const
Return an efficient buffer size for the underlying output mechanism.
raw_ostream & write(unsigned char C)
void SetUnbuffered()
Set the stream to be unbuffered.
virtual bool is_displayed() const
This function determines if this stream is connected to a "tty" or "console" window.
raw_ostream & indent(unsigned NumSpaces)
indent - Insert 'NumSpaces' spaces.
static constexpr Colors SAVEDCOLOR
uint8_t[16] uuid_t
Output a formatted UUID with dash separators.
virtual void enable_colors(bool enable)
size_t GetNumBytesInBuffer() const
OStreamKind get_kind() const
void SetBuffered()
Set the stream to be buffered, with an automatically determined buffer size.
raw_pwrite_stream(bool Unbuffered=false, OStreamKind K=OStreamKind::OK_OStream)
A raw_ostream that writes to an SmallVector or SmallString.
static bool classof(const raw_ostream *OS)
static LLVM_ABI std::error_code SafelyCloseFileDescriptor(int FD)
static LLVM_ABI bool ColorNeedsFlush()
Whether changing colors requires the output to be flushed.
static LLVM_ABI const char * ResetColor()
Resets the terminals colors, or returns an escape sequence to do so.
static LLVM_ABI bool FileDescriptorIsDisplayed(int fd)
This function determines if the given file descriptor is connected to a "tty" or "console" window.
static LLVM_ABI const char * OutputColor(char c, bool bold, bool bg)
This function returns the colorcode escape sequences.
static LLVM_ABI const char * OutputBold(bool bg)
Same as OutputColor, but only enables the bold attribute.
static LLVM_ABI bool FileDescriptorHasColors(int fd)
This function determines if the given file descriptor is displayd and supports colors.
static LLVM_ABI const char * OutputReverse()
This function returns the escape sequence to reverse forground and background colors.
RAII class that facilitates file locking.
static LLVM_ABI Expected< TempFile > create(const Twine &Model, unsigned Mode=all_read|all_write, OpenFlags ExtraFlags=OF_None)
This creates a temporary file with createUniqueFile and schedules it for deletion with sys::RemoveFil...
Represents the result of a call to sys::fs::status().
Definition FileSystem.h:222
@ C
The default llvm calling convention, compatible with C.
Definition CallingConv.h:34
std::error_code openFileForReadWrite(const Twine &Name, int &ResultFD, CreationDisposition Disp, OpenFlags Flags, unsigned Mode=0666)
Opens the file with the given name in a write-only or read-write mode, returning its open file descri...
LLVM_ABI std::error_code lockFile(int FD, LockKind Kind=LockKind::Exclusive)
Lock the file.
std::error_code openFileForWrite(const Twine &Name, int &ResultFD, CreationDisposition Disp=CD_CreateAlways, OpenFlags Flags=OF_None, unsigned Mode=0666)
Opens the file with the given name in a write-only or read-write mode, returning its open file descri...
LLVM_ABI std::error_code tryLockFile(int FD, std::chrono::milliseconds Timeout=std::chrono::milliseconds(0), LockKind Kind=LockKind::Exclusive)
Try to locks the file during the specified time.
LLVM_ABI std::error_code ChangeStdoutMode(fs::OpenFlags Flags)
This is an optimization pass for GlobalISel generic memory operations.
@ Offset
Definition DWP.cpp:477
@ Length
Definition DWP.cpp:477
LLVM_ABI bool RunningWindows8OrGreater()
Determines if the program is running on Windows 8 or newer.
Error createFileError(const Twine &F, Error E)
Concatenate a source file path and/or name with an Error.
Definition Error.h:1399
unsigned Log2_64_Ceil(uint64_t Value)
Return the ceil log base 2 of the specified value, 64 if the value is zero.
Definition MathExtras.h:350
LLVM_ABI raw_fd_ostream & outs()
This returns a reference to a raw_fd_ostream for standard output.
LLVM_ABI void write_integer(raw_ostream &S, unsigned int N, size_t MinDigits, IntegerStyle Style)
Error joinErrors(Error E1, Error E2)
Concatenate errors.
Definition Error.h:442
LLVM_ABI Error write(MCStreamer &Out, ArrayRef< std::string > Inputs, OnCuIndexOverflow OverflowOptValue)
Definition DWP.cpp:622
char hexdigit(unsigned X, bool LowerCase=false)
hexdigit - Return the hexadecimal character for the given number X (which should be less than 16).
LLVM_ABI Error writeToOutput(StringRef OutputFileName, std::function< Error(raw_ostream &)> Write)
This helper creates an output stream and then passes it to Write.
LLVM_ABI raw_ostream & nulls()
This returns a reference to a raw_ostream which simply discards output.
format_object< Ts... > format(const char *Fmt, const Ts &... Vals)
These are helper functions used to produce formatted output.
Definition Format.h:129
@ Success
The lock was released successfully.
@ Timeout
Reached timeout while waiting for the owner to release the lock.
LLVM_ABI raw_fd_ostream & errs()
This returns a reference to a raw_ostream for standard error.
FunctionAddr VTableAddr uintptr_t uintptr_t Data
Definition InstrProf.h:189
uint64_t alignTo(uint64_t Size, Align A)
Returns a multiple of A needed to store Size bytes.
Definition Alignment.h:144
LLVM_ABI void write_hex(raw_ostream &S, uint64_t N, HexPrintStyle Style, std::optional< size_t > Width=std::nullopt)
LLVM_ABI void write_double(raw_ostream &S, double D, FloatStyle Style, std::optional< size_t > Precision=std::nullopt)
bool isPrint(char C)
Checks whether character C is printable.
LLVM_ABI Error errorCodeToError(std::error_code EC)
Helper for converting an std::error_code to a Error.
Definition Error.cpp:111
std::error_code errnoAsErrorCode()
Helper to get errno as an std::error_code.
Definition Error.h:1240
LLVM_ABI void reportFatalUsageError(Error Err)
Report a fatal error that does not indicate a bug in LLVM.
Definition Error.cpp:180
static int getFD(StringRef Filename, std::error_code &EC, sys::fs::CreationDisposition Disp, sys::fs::FileAccess Access, sys::fs::OpenFlags Flags)
static raw_ostream & write_padding(raw_ostream &OS, unsigned NumChars)
#define N