]> CyberLeo.Net >> Repos - FreeBSD/releng/9.2.git/blob - contrib/llvm/include/llvm/Support/FormattedStream.h
- Copy stable/9 to releng/9.2 as part of the 9.2-RELEASE cycle.
[FreeBSD/releng/9.2.git] / contrib / llvm / include / llvm / Support / FormattedStream.h
1 //===-- llvm/Support/FormattedStream.h - 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 raw_ostream implementations for streams to do
11 // things like pretty-print comments.
12 //
13 //===----------------------------------------------------------------------===//
14
15 #ifndef LLVM_SUPPORT_FORMATTEDSTREAM_H
16 #define LLVM_SUPPORT_FORMATTEDSTREAM_H
17
18 #include "llvm/Support/raw_ostream.h"
19
20 namespace llvm {
21
22 /// formatted_raw_ostream - A raw_ostream that wraps another one and keeps track
23 /// of column position, allowing padding out to specific column boundaries.
24 ///
25 class formatted_raw_ostream : public raw_ostream {
26 public:
27   /// DELETE_STREAM - Tell the destructor to delete the held stream.
28   ///
29   static const bool DELETE_STREAM = true;
30
31   /// PRESERVE_STREAM - Tell the destructor to not delete the held
32   /// stream.
33   ///
34   static const bool PRESERVE_STREAM = false;
35
36 private:
37   /// TheStream - The real stream we output to. We set it to be
38   /// unbuffered, since we're already doing our own buffering.
39   ///
40   raw_ostream *TheStream;
41
42   /// DeleteStream - Do we need to delete TheStream in the
43   /// destructor?
44   ///
45   bool DeleteStream;
46
47   /// ColumnScanned - The current output column of the data that's
48   /// been flushed and the portion of the buffer that's been
49   /// scanned.  The column scheme is zero-based.
50   ///
51   unsigned ColumnScanned;
52
53   /// Scanned - This points to one past the last character in the
54   /// buffer we've scanned.
55   ///
56   const char *Scanned;
57
58   virtual void write_impl(const char *Ptr, size_t Size) LLVM_OVERRIDE;
59
60   /// current_pos - Return the current position within the stream,
61   /// not counting the bytes currently in the buffer.
62   virtual uint64_t current_pos() const LLVM_OVERRIDE {
63     // Our current position in the stream is all the contents which have been
64     // written to the underlying stream (*not* the current position of the
65     // underlying stream).
66     return TheStream->tell();
67   }
68
69   /// ComputeColumn - Examine the given output buffer and figure out which
70   /// column we end up in after output.
71   ///
72   void ComputeColumn(const char *Ptr, size_t size);
73
74 public:
75   /// formatted_raw_ostream - Open the specified file for
76   /// writing. If an error occurs, information about the error is
77   /// put into ErrorInfo, and the stream should be immediately
78   /// destroyed; the string will be empty if no error occurred.
79   ///
80   /// As a side effect, the given Stream is set to be Unbuffered.
81   /// This is because formatted_raw_ostream does its own buffering,
82   /// so it doesn't want another layer of buffering to be happening
83   /// underneath it.
84   ///
85   formatted_raw_ostream(raw_ostream &Stream, bool Delete = false) 
86     : raw_ostream(), TheStream(0), DeleteStream(false), ColumnScanned(0) {
87     setStream(Stream, Delete);
88   }
89   explicit formatted_raw_ostream()
90     : raw_ostream(), TheStream(0), DeleteStream(false), ColumnScanned(0) {
91     Scanned = 0;
92   }
93
94   ~formatted_raw_ostream() {
95     flush();
96     releaseStream();
97   }
98
99   void setStream(raw_ostream &Stream, bool Delete = false) {
100     releaseStream();
101
102     TheStream = &Stream;
103     DeleteStream = Delete;
104
105     // This formatted_raw_ostream inherits from raw_ostream, so it'll do its
106     // own buffering, and it doesn't need or want TheStream to do another
107     // layer of buffering underneath. Resize the buffer to what TheStream
108     // had been using, and tell TheStream not to do its own buffering.
109     if (size_t BufferSize = TheStream->GetBufferSize())
110       SetBufferSize(BufferSize);
111     else
112       SetUnbuffered();
113     TheStream->SetUnbuffered();
114
115     Scanned = 0;
116   }
117
118   /// PadToColumn - Align the output to some column number.  If the current
119   /// column is already equal to or more than NewCol, PadToColumn inserts one
120   /// space.
121   ///
122   /// \param NewCol - The column to move to.
123   formatted_raw_ostream &PadToColumn(unsigned NewCol);
124
125 private:
126   void releaseStream() {
127     // Delete the stream if needed. Otherwise, transfer the buffer
128     // settings from this raw_ostream back to the underlying stream.
129     if (!TheStream)
130       return;
131     if (DeleteStream)
132       delete TheStream;
133     else if (size_t BufferSize = GetBufferSize())
134       TheStream->SetBufferSize(BufferSize);
135     else
136       TheStream->SetUnbuffered();
137   }
138 };
139
140 /// fouts() - This returns a reference to a formatted_raw_ostream for
141 /// standard output.  Use it like: fouts() << "foo" << "bar";
142 formatted_raw_ostream &fouts();
143
144 /// ferrs() - This returns a reference to a formatted_raw_ostream for
145 /// standard error.  Use it like: ferrs() << "foo" << "bar";
146 formatted_raw_ostream &ferrs();
147
148 /// fdbgs() - This returns a reference to a formatted_raw_ostream for
149 /// debug output.  Use it like: fdbgs() << "foo" << "bar";
150 formatted_raw_ostream &fdbgs();
151
152 } // end llvm namespace
153
154
155 #endif