]>
Commit | Line | Data |
---|---|---|
223e47cc LB |
1 | //===-- llvm/Support/FormattedStream.cpp - Formatted streams ----*- C++ -*-===// |
2 | // | |
3 | // The LLVM Compiler Infrastructure | |
4 | // | |
5 | // This file is distributed under the University of Illinois Open Source | |
6 | // License. See LICENSE.TXT for details. | |
7 | // | |
8 | //===----------------------------------------------------------------------===// | |
9 | // | |
10 | // This file contains the implementation of formatted_raw_ostream. | |
11 | // | |
12 | //===----------------------------------------------------------------------===// | |
13 | ||
14 | #include "llvm/Support/Debug.h" | |
15 | #include "llvm/Support/FormattedStream.h" | |
16 | #include <algorithm> | |
17 | ||
18 | using namespace llvm; | |
19 | ||
1a4d82fc JJ |
20 | /// UpdatePosition - Examine the given char sequence and figure out which |
21 | /// column we end up in after output, and how many line breaks are contained. | |
223e47cc | 22 | /// |
1a4d82fc JJ |
23 | static void UpdatePosition(std::pair<unsigned, unsigned> &Position, const char *Ptr, size_t Size) { |
24 | unsigned &Column = Position.first; | |
25 | unsigned &Line = Position.second; | |
223e47cc | 26 | |
1a4d82fc JJ |
27 | // Keep track of the current column and line by scanning the string for |
28 | // special characters | |
223e47cc LB |
29 | for (const char *End = Ptr + Size; Ptr != End; ++Ptr) { |
30 | ++Column; | |
1a4d82fc JJ |
31 | switch (*Ptr) { |
32 | case '\n': | |
33 | Line += 1; | |
34 | case '\r': | |
223e47cc | 35 | Column = 0; |
1a4d82fc JJ |
36 | break; |
37 | case '\t': | |
223e47cc LB |
38 | // Assumes tab stop = 8 characters. |
39 | Column += (8 - (Column & 0x7)) & 0x7; | |
1a4d82fc JJ |
40 | break; |
41 | } | |
223e47cc | 42 | } |
223e47cc LB |
43 | } |
44 | ||
1a4d82fc JJ |
45 | /// ComputePosition - Examine the current output and update line and column |
46 | /// counts. | |
47 | void formatted_raw_ostream::ComputePosition(const char *Ptr, size_t Size) { | |
223e47cc LB |
48 | // If our previous scan pointer is inside the buffer, assume we already |
49 | // scanned those bytes. This depends on raw_ostream to not change our buffer | |
50 | // in unexpected ways. | |
1a4d82fc | 51 | if (Ptr <= Scanned && Scanned <= Ptr + Size) |
223e47cc LB |
52 | // Scan all characters added since our last scan to determine the new |
53 | // column. | |
1a4d82fc JJ |
54 | UpdatePosition(Position, Scanned, Size - (Scanned - Ptr)); |
55 | else | |
56 | UpdatePosition(Position, Ptr, Size); | |
223e47cc LB |
57 | |
58 | // Update the scanning pointer. | |
59 | Scanned = Ptr + Size; | |
60 | } | |
61 | ||
62 | /// PadToColumn - Align the output to some column number. | |
63 | /// | |
64 | /// \param NewCol - The column to move to. | |
65 | /// | |
66 | formatted_raw_ostream &formatted_raw_ostream::PadToColumn(unsigned NewCol) { | |
67 | // Figure out what's in the buffer and add it to the column count. | |
1a4d82fc | 68 | ComputePosition(getBufferStart(), GetNumBytesInBuffer()); |
223e47cc LB |
69 | |
70 | // Output spaces until we reach the desired column. | |
1a4d82fc | 71 | indent(std::max(int(NewCol - getColumn()), 1)); |
223e47cc LB |
72 | return *this; |
73 | } | |
74 | ||
75 | void formatted_raw_ostream::write_impl(const char *Ptr, size_t Size) { | |
76 | // Figure out what's in the buffer and add it to the column count. | |
1a4d82fc | 77 | ComputePosition(Ptr, Size); |
223e47cc LB |
78 | |
79 | // Write the data to the underlying stream (which is unbuffered, so | |
80 | // the data will be immediately written out). | |
81 | TheStream->write(Ptr, Size); | |
82 | ||
83 | // Reset the scanning pointer. | |
1a4d82fc | 84 | Scanned = nullptr; |
223e47cc LB |
85 | } |
86 | ||
87 | /// fouts() - This returns a reference to a formatted_raw_ostream for | |
88 | /// standard output. Use it like: fouts() << "foo" << "bar"; | |
89 | formatted_raw_ostream &llvm::fouts() { | |
90 | static formatted_raw_ostream S(outs()); | |
91 | return S; | |
92 | } | |
93 | ||
94 | /// ferrs() - This returns a reference to a formatted_raw_ostream for | |
95 | /// standard error. Use it like: ferrs() << "foo" << "bar"; | |
96 | formatted_raw_ostream &llvm::ferrs() { | |
97 | static formatted_raw_ostream S(errs()); | |
98 | return S; | |
99 | } | |
100 | ||
101 | /// fdbgs() - This returns a reference to a formatted_raw_ostream for | |
102 | /// the debug stream. Use it like: fdbgs() << "foo" << "bar"; | |
103 | formatted_raw_ostream &llvm::fdbgs() { | |
104 | static formatted_raw_ostream S(dbgs()); | |
105 | return S; | |
106 | } |